@@ -14,1264 +14,1264 @@ |
||
14 | 14 | { |
15 | 15 | |
16 | 16 | |
17 | - /** |
|
18 | - * Extend_Events_Admin_Page constructor. |
|
19 | - * |
|
20 | - * @param bool $routing |
|
21 | - */ |
|
22 | - public function __construct($routing = true) |
|
23 | - { |
|
24 | - parent::__construct($routing); |
|
25 | - if (! defined('EVENTS_CAF_TEMPLATE_PATH')) { |
|
26 | - define('EVENTS_CAF_TEMPLATE_PATH', EE_CORE_CAF_ADMIN_EXTEND . 'events/templates/'); |
|
27 | - define('EVENTS_CAF_ASSETS', EE_CORE_CAF_ADMIN_EXTEND . 'events/assets/'); |
|
28 | - define('EVENTS_CAF_ASSETS_URL', EE_CORE_CAF_ADMIN_EXTEND_URL . 'events/assets/'); |
|
29 | - } |
|
30 | - } |
|
31 | - |
|
32 | - |
|
33 | - /** |
|
34 | - * Sets routes. |
|
35 | - */ |
|
36 | - protected function _extend_page_config() |
|
37 | - { |
|
38 | - $this->_admin_base_path = EE_CORE_CAF_ADMIN_EXTEND . 'events'; |
|
39 | - //is there a evt_id in the request? |
|
40 | - $evt_id = ! empty($this->_req_data['EVT_ID']) && ! is_array($this->_req_data['EVT_ID']) |
|
41 | - ? $this->_req_data['EVT_ID'] |
|
42 | - : 0; |
|
43 | - $evt_id = ! empty($this->_req_data['post']) ? $this->_req_data['post'] : $evt_id; |
|
44 | - //tkt_id? |
|
45 | - $tkt_id = ! empty($this->_req_data['TKT_ID']) && ! is_array($this->_req_data['TKT_ID']) |
|
46 | - ? $this->_req_data['TKT_ID'] |
|
47 | - : 0; |
|
48 | - $new_page_routes = array( |
|
49 | - 'duplicate_event' => array( |
|
50 | - 'func' => '_duplicate_event', |
|
51 | - 'capability' => 'ee_edit_event', |
|
52 | - 'obj_id' => $evt_id, |
|
53 | - 'noheader' => true, |
|
54 | - ), |
|
55 | - 'ticket_list_table' => array( |
|
56 | - 'func' => '_tickets_overview_list_table', |
|
57 | - 'capability' => 'ee_read_default_tickets', |
|
58 | - ), |
|
59 | - 'trash_ticket' => array( |
|
60 | - 'func' => '_trash_or_restore_ticket', |
|
61 | - 'capability' => 'ee_delete_default_ticket', |
|
62 | - 'obj_id' => $tkt_id, |
|
63 | - 'noheader' => true, |
|
64 | - 'args' => array('trash' => true), |
|
65 | - ), |
|
66 | - 'trash_tickets' => array( |
|
67 | - 'func' => '_trash_or_restore_ticket', |
|
68 | - 'capability' => 'ee_delete_default_tickets', |
|
69 | - 'noheader' => true, |
|
70 | - 'args' => array('trash' => true), |
|
71 | - ), |
|
72 | - 'restore_ticket' => array( |
|
73 | - 'func' => '_trash_or_restore_ticket', |
|
74 | - 'capability' => 'ee_delete_default_ticket', |
|
75 | - 'obj_id' => $tkt_id, |
|
76 | - 'noheader' => true, |
|
77 | - ), |
|
78 | - 'restore_tickets' => array( |
|
79 | - 'func' => '_trash_or_restore_ticket', |
|
80 | - 'capability' => 'ee_delete_default_tickets', |
|
81 | - 'noheader' => true, |
|
82 | - ), |
|
83 | - 'delete_ticket' => array( |
|
84 | - 'func' => '_delete_ticket', |
|
85 | - 'capability' => 'ee_delete_default_ticket', |
|
86 | - 'obj_id' => $tkt_id, |
|
87 | - 'noheader' => true, |
|
88 | - ), |
|
89 | - 'delete_tickets' => array( |
|
90 | - 'func' => '_delete_ticket', |
|
91 | - 'capability' => 'ee_delete_default_tickets', |
|
92 | - 'noheader' => true, |
|
93 | - ), |
|
94 | - 'import_page' => array( |
|
95 | - 'func' => '_import_page', |
|
96 | - 'capability' => 'import', |
|
97 | - ), |
|
98 | - 'import' => array( |
|
99 | - 'func' => '_import_events', |
|
100 | - 'capability' => 'import', |
|
101 | - 'noheader' => true, |
|
102 | - ), |
|
103 | - 'import_events' => array( |
|
104 | - 'func' => '_import_events', |
|
105 | - 'capability' => 'import', |
|
106 | - 'noheader' => true, |
|
107 | - ), |
|
108 | - 'export_events' => array( |
|
109 | - 'func' => '_events_export', |
|
110 | - 'capability' => 'export', |
|
111 | - 'noheader' => true, |
|
112 | - ), |
|
113 | - 'export_categories' => array( |
|
114 | - 'func' => '_categories_export', |
|
115 | - 'capability' => 'export', |
|
116 | - 'noheader' => true, |
|
117 | - ), |
|
118 | - 'sample_export_file' => array( |
|
119 | - 'func' => '_sample_export_file', |
|
120 | - 'capability' => 'export', |
|
121 | - 'noheader' => true, |
|
122 | - ), |
|
123 | - 'update_template_settings' => array( |
|
124 | - 'func' => '_update_template_settings', |
|
125 | - 'capability' => 'manage_options', |
|
126 | - 'noheader' => true, |
|
127 | - ), |
|
128 | - ); |
|
129 | - $this->_page_routes = array_merge($this->_page_routes, $new_page_routes); |
|
130 | - //partial route/config override |
|
131 | - $this->_page_config['import_events']['metaboxes'] = $this->_default_espresso_metaboxes; |
|
132 | - $this->_page_config['create_new']['metaboxes'][] = '_premium_event_editor_meta_boxes'; |
|
133 | - $this->_page_config['create_new']['qtips'][] = 'EE_Event_Editor_Tips'; |
|
134 | - $this->_page_config['edit']['qtips'][] = 'EE_Event_Editor_Tips'; |
|
135 | - $this->_page_config['edit']['metaboxes'][] = '_premium_event_editor_meta_boxes'; |
|
136 | - $this->_page_config['default']['list_table'] = 'Extend_Events_Admin_List_Table'; |
|
137 | - //add tickets tab but only if there are more than one default ticket! |
|
138 | - $tkt_count = EEM_Ticket::instance()->count_deleted_and_undeleted( |
|
139 | - array(array('TKT_is_default' => 1)), |
|
140 | - 'TKT_ID', |
|
141 | - true |
|
142 | - ); |
|
143 | - if ($tkt_count > 1) { |
|
144 | - $new_page_config = array( |
|
145 | - 'ticket_list_table' => array( |
|
146 | - 'nav' => array( |
|
147 | - 'label' => esc_html__('Default Tickets', 'event_espresso'), |
|
148 | - 'order' => 60, |
|
149 | - ), |
|
150 | - 'list_table' => 'Tickets_List_Table', |
|
151 | - 'require_nonce' => false, |
|
152 | - ), |
|
153 | - ); |
|
154 | - } |
|
155 | - //template settings |
|
156 | - $new_page_config['template_settings'] = array( |
|
157 | - 'nav' => array( |
|
158 | - 'label' => esc_html__('Templates', 'event_espresso'), |
|
159 | - 'order' => 30, |
|
160 | - ), |
|
161 | - 'metaboxes' => array_merge($this->_default_espresso_metaboxes, array('_publish_post_box')), |
|
162 | - 'help_tabs' => array( |
|
163 | - 'general_settings_templates_help_tab' => array( |
|
164 | - 'title' => esc_html__('Templates', 'event_espresso'), |
|
165 | - 'filename' => 'general_settings_templates', |
|
166 | - ), |
|
167 | - ), |
|
168 | - 'help_tour' => array('Templates_Help_Tour'), |
|
169 | - 'require_nonce' => false, |
|
170 | - ); |
|
171 | - $this->_page_config = array_merge($this->_page_config, $new_page_config); |
|
172 | - //add filters and actions |
|
173 | - //modifying _views |
|
174 | - add_filter( |
|
175 | - 'FHEE_event_datetime_metabox_add_additional_date_time_template', |
|
176 | - array($this, 'add_additional_datetime_button'), |
|
177 | - 10, |
|
178 | - 2 |
|
179 | - ); |
|
180 | - add_filter( |
|
181 | - 'FHEE_event_datetime_metabox_clone_button_template', |
|
182 | - array($this, 'add_datetime_clone_button'), |
|
183 | - 10, |
|
184 | - 2 |
|
185 | - ); |
|
186 | - add_filter( |
|
187 | - 'FHEE_event_datetime_metabox_timezones_template', |
|
188 | - array($this, 'datetime_timezones_template'), |
|
189 | - 10, |
|
190 | - 2 |
|
191 | - ); |
|
192 | - //filters for event list table |
|
193 | - add_filter('FHEE__Extend_Events_Admin_List_Table__filters', array($this, 'list_table_filters'), 10, 2); |
|
194 | - add_filter( |
|
195 | - 'FHEE__Events_Admin_List_Table__column_actions__action_links', |
|
196 | - array($this, 'extra_list_table_actions'), |
|
197 | - 10, |
|
198 | - 2 |
|
199 | - ); |
|
200 | - //legend item |
|
201 | - add_filter('FHEE__Events_Admin_Page___event_legend_items__items', array($this, 'additional_legend_items')); |
|
202 | - add_action('admin_init', array($this, 'admin_init')); |
|
203 | - //heartbeat stuff |
|
204 | - add_filter('heartbeat_received', array($this, 'heartbeat_response'), 10, 2); |
|
205 | - } |
|
206 | - |
|
207 | - |
|
208 | - /** |
|
209 | - * admin_init |
|
210 | - */ |
|
211 | - public function admin_init() |
|
212 | - { |
|
213 | - EE_Registry::$i18n_js_strings = array_merge( |
|
214 | - EE_Registry::$i18n_js_strings, |
|
215 | - array( |
|
216 | - 'image_confirm' => esc_html__( |
|
217 | - 'Do you really want to delete this image? Please remember to update your event to complete the removal.', |
|
218 | - 'event_espresso' |
|
219 | - ), |
|
220 | - 'event_starts_on' => esc_html__('Event Starts on', 'event_espresso'), |
|
221 | - 'event_ends_on' => esc_html__('Event Ends on', 'event_espresso'), |
|
222 | - 'event_datetime_actions' => esc_html__('Actions', 'event_espresso'), |
|
223 | - 'event_clone_dt_msg' => esc_html__('Clone this Event Date and Time', 'event_espresso'), |
|
224 | - 'remove_event_dt_msg' => esc_html__('Remove this Event Time', 'event_espresso'), |
|
225 | - ) |
|
226 | - ); |
|
227 | - } |
|
228 | - |
|
229 | - |
|
230 | - /** |
|
231 | - * This will be used to listen for any heartbeat data packages coming via the WordPress heartbeat API and handle |
|
232 | - * accordingly. |
|
233 | - * |
|
234 | - * @param array $response The existing heartbeat response array. |
|
235 | - * @param array $data The incoming data package. |
|
236 | - * @return array possibly appended response. |
|
237 | - */ |
|
238 | - public function heartbeat_response($response, $data) |
|
239 | - { |
|
240 | - /** |
|
241 | - * check whether count of tickets is approaching the potential |
|
242 | - * limits for the server. |
|
243 | - */ |
|
244 | - if (! empty($data['input_count'])) { |
|
245 | - $response['max_input_vars_check'] = EE_Registry::instance()->CFG->environment->max_input_vars_limit_check( |
|
246 | - $data['input_count'] |
|
247 | - ); |
|
248 | - } |
|
249 | - return $response; |
|
250 | - } |
|
251 | - |
|
252 | - |
|
253 | - /** |
|
254 | - * Add per page screen options to the default ticket list table view. |
|
255 | - */ |
|
256 | - protected function _add_screen_options_ticket_list_table() |
|
257 | - { |
|
258 | - $this->_per_page_screen_option(); |
|
259 | - } |
|
260 | - |
|
261 | - |
|
262 | - /** |
|
263 | - * @param string $return |
|
264 | - * @param int $id |
|
265 | - * @param string $new_title |
|
266 | - * @param string $new_slug |
|
267 | - * @return string |
|
268 | - */ |
|
269 | - public function extra_permalink_field_buttons($return, $id, $new_title, $new_slug) |
|
270 | - { |
|
271 | - $return = parent::extra_permalink_field_buttons($return, $id, $new_title, $new_slug); |
|
272 | - //make sure this is only when editing |
|
273 | - if (! empty($id)) { |
|
274 | - $href = EE_Admin_Page::add_query_args_and_nonce( |
|
275 | - array('action' => 'duplicate_event', 'EVT_ID' => $id), |
|
276 | - $this->_admin_base_url |
|
277 | - ); |
|
278 | - $title = esc_attr__('Duplicate Event', 'event_espresso'); |
|
279 | - $return .= '<a href="' |
|
280 | - . $href |
|
281 | - . '" title="' |
|
282 | - . $title |
|
283 | - . '" id="ee-duplicate-event-button" class="button button-small" value="duplicate_event">' |
|
284 | - . $title |
|
285 | - . '</button>'; |
|
286 | - } |
|
287 | - return $return; |
|
288 | - } |
|
289 | - |
|
290 | - |
|
291 | - /** |
|
292 | - * Set the list table views for the default ticket list table view. |
|
293 | - */ |
|
294 | - public function _set_list_table_views_ticket_list_table() |
|
295 | - { |
|
296 | - $this->_views = array( |
|
297 | - 'all' => array( |
|
298 | - 'slug' => 'all', |
|
299 | - 'label' => esc_html__('All', 'event_espresso'), |
|
300 | - 'count' => 0, |
|
301 | - 'bulk_action' => array( |
|
302 | - 'trash_tickets' => esc_html__('Move to Trash', 'event_espresso'), |
|
303 | - ), |
|
304 | - ), |
|
305 | - 'trashed' => array( |
|
306 | - 'slug' => 'trashed', |
|
307 | - 'label' => esc_html__('Trash', 'event_espresso'), |
|
308 | - 'count' => 0, |
|
309 | - 'bulk_action' => array( |
|
310 | - 'restore_tickets' => esc_html__('Restore from Trash', 'event_espresso'), |
|
311 | - 'delete_tickets' => esc_html__('Delete Permanently', 'event_espresso'), |
|
312 | - ), |
|
313 | - ), |
|
314 | - ); |
|
315 | - } |
|
316 | - |
|
317 | - |
|
318 | - /** |
|
319 | - * Enqueue scripts and styles for the event editor. |
|
320 | - */ |
|
321 | - public function load_scripts_styles_edit() |
|
322 | - { |
|
323 | - wp_register_script( |
|
324 | - 'ee-event-editor-heartbeat', |
|
325 | - EVENTS_CAF_ASSETS_URL . 'event-editor-heartbeat.js', |
|
326 | - array('ee_admin_js', 'heartbeat'), |
|
327 | - EVENT_ESPRESSO_VERSION, |
|
328 | - true |
|
329 | - ); |
|
330 | - wp_enqueue_script('ee-accounting'); |
|
331 | - //styles |
|
332 | - wp_enqueue_style('espresso-ui-theme'); |
|
333 | - wp_enqueue_script('event_editor_js'); |
|
334 | - wp_enqueue_script('ee-event-editor-heartbeat'); |
|
335 | - } |
|
336 | - |
|
337 | - |
|
338 | - /** |
|
339 | - * Returns template for the additional datetime. |
|
340 | - * @param $template |
|
341 | - * @param $template_args |
|
342 | - * @return mixed |
|
343 | - * @throws DomainException |
|
344 | - */ |
|
345 | - public function add_additional_datetime_button($template, $template_args) |
|
346 | - { |
|
347 | - return EEH_Template::display_template( |
|
348 | - EVENTS_CAF_TEMPLATE_PATH . 'event_datetime_add_additional_time.template.php', |
|
349 | - $template_args, |
|
350 | - true |
|
351 | - ); |
|
352 | - } |
|
353 | - |
|
354 | - |
|
355 | - /** |
|
356 | - * Returns the template for cloning a datetime. |
|
357 | - * @param $template |
|
358 | - * @param $template_args |
|
359 | - * @return mixed |
|
360 | - * @throws DomainException |
|
361 | - */ |
|
362 | - public function add_datetime_clone_button($template, $template_args) |
|
363 | - { |
|
364 | - return EEH_Template::display_template( |
|
365 | - EVENTS_CAF_TEMPLATE_PATH . 'event_datetime_metabox_clone_button.template.php', |
|
366 | - $template_args, |
|
367 | - true |
|
368 | - ); |
|
369 | - } |
|
370 | - |
|
371 | - |
|
372 | - /** |
|
373 | - * Returns the template for datetime timezones. |
|
374 | - * @param $template |
|
375 | - * @param $template_args |
|
376 | - * @return mixed |
|
377 | - * @throws DomainException |
|
378 | - */ |
|
379 | - public function datetime_timezones_template($template, $template_args) |
|
380 | - { |
|
381 | - return EEH_Template::display_template( |
|
382 | - EVENTS_CAF_TEMPLATE_PATH . 'event_datetime_timezones.template.php', |
|
383 | - $template_args, |
|
384 | - true |
|
385 | - ); |
|
386 | - } |
|
387 | - |
|
388 | - |
|
389 | - /** |
|
390 | - * Sets the views for the default list table view. |
|
391 | - */ |
|
392 | - protected function _set_list_table_views_default() |
|
393 | - { |
|
394 | - parent::_set_list_table_views_default(); |
|
395 | - $new_views = array( |
|
396 | - 'today' => array( |
|
397 | - 'slug' => 'today', |
|
398 | - 'label' => esc_html__('Today', 'event_espresso'), |
|
399 | - 'count' => $this->total_events_today(), |
|
400 | - 'bulk_action' => array( |
|
401 | - 'trash_events' => esc_html__('Move to Trash', 'event_espresso'), |
|
402 | - ), |
|
403 | - ), |
|
404 | - 'month' => array( |
|
405 | - 'slug' => 'month', |
|
406 | - 'label' => esc_html__('This Month', 'event_espresso'), |
|
407 | - 'count' => $this->total_events_this_month(), |
|
408 | - 'bulk_action' => array( |
|
409 | - 'trash_events' => esc_html__('Move to Trash', 'event_espresso'), |
|
410 | - ), |
|
411 | - ), |
|
412 | - ); |
|
413 | - $this->_views = array_merge($this->_views, $new_views); |
|
414 | - } |
|
415 | - |
|
416 | - |
|
417 | - /** |
|
418 | - * Returns the extra action links for the default list table view. |
|
419 | - * @param array $action_links |
|
420 | - * @param \EE_Event $event |
|
421 | - * @return array |
|
422 | - * @throws EE_Error |
|
423 | - */ |
|
424 | - public function extra_list_table_actions(array $action_links, \EE_Event $event) |
|
425 | - { |
|
426 | - if (EE_Registry::instance()->CAP->current_user_can( |
|
427 | - 'ee_read_registrations', |
|
428 | - 'espresso_registrations_reports', |
|
429 | - $event->ID() |
|
430 | - ) |
|
431 | - ) { |
|
432 | - $reports_query_args = array( |
|
433 | - 'action' => 'reports', |
|
434 | - 'EVT_ID' => $event->ID(), |
|
435 | - ); |
|
436 | - $reports_link = EE_Admin_Page::add_query_args_and_nonce($reports_query_args, REG_ADMIN_URL); |
|
437 | - $action_links[] = '<a href="' |
|
438 | - . $reports_link |
|
439 | - . '" title="' |
|
440 | - . esc_attr__('View Report', 'event_espresso') |
|
441 | - . '"><div class="dashicons dashicons-chart-bar"></div></a>' |
|
442 | - . "\n\t"; |
|
443 | - } |
|
444 | - if (EE_Registry::instance()->CAP->current_user_can('ee_read_global_messages', 'view_filtered_messages')) { |
|
445 | - EE_Registry::instance()->load_helper('MSG_Template'); |
|
446 | - $action_links[] = EEH_MSG_Template::get_message_action_link( |
|
447 | - 'see_notifications_for', |
|
448 | - null, |
|
449 | - array('EVT_ID' => $event->ID()) |
|
450 | - ); |
|
451 | - } |
|
452 | - return $action_links; |
|
453 | - } |
|
454 | - |
|
455 | - |
|
456 | - /** |
|
457 | - * @param $items |
|
458 | - * @return mixed |
|
459 | - */ |
|
460 | - public function additional_legend_items($items) |
|
461 | - { |
|
462 | - if (EE_Registry::instance()->CAP->current_user_can( |
|
463 | - 'ee_read_registrations', |
|
464 | - 'espresso_registrations_reports' |
|
465 | - ) |
|
466 | - ) { |
|
467 | - $items['reports'] = array( |
|
468 | - 'class' => 'dashicons dashicons-chart-bar', |
|
469 | - 'desc' => esc_html__('Event Reports', 'event_espresso'), |
|
470 | - ); |
|
471 | - } |
|
472 | - if (EE_Registry::instance()->CAP->current_user_can('ee_read_global_messages', 'view_filtered_messages')) { |
|
473 | - $related_for_icon = EEH_MSG_Template::get_message_action_icon('see_notifications_for'); |
|
474 | - if (isset($related_for_icon['css_class']) && isset($related_for_icon['label'])) { |
|
475 | - $items['view_related_messages'] = array( |
|
476 | - 'class' => $related_for_icon['css_class'], |
|
477 | - 'desc' => $related_for_icon['label'], |
|
478 | - ); |
|
479 | - } |
|
480 | - } |
|
481 | - return $items; |
|
482 | - } |
|
483 | - |
|
484 | - |
|
485 | - /** |
|
486 | - * This is the callback method for the duplicate event route |
|
487 | - * Method looks for 'EVT_ID' in the request and retrieves that event and its details and duplicates them |
|
488 | - * into a new event. We add a hook so that any plugins that add extra event details can hook into this |
|
489 | - * action. Note that the dupe will have **DUPLICATE** as its title and slug. |
|
490 | - * After duplication the redirect is to the new event edit page. |
|
491 | - * |
|
492 | - * @return void |
|
493 | - * @access protected |
|
494 | - * @throws EE_Error If EE_Event is not available with given ID |
|
495 | - */ |
|
496 | - protected function _duplicate_event() |
|
497 | - { |
|
498 | - // first make sure the ID for the event is in the request. |
|
499 | - // If it isn't then we need to bail and redirect back to overview list table (cause how did we get here?) |
|
500 | - if (! isset($this->_req_data['EVT_ID'])) { |
|
501 | - EE_Error::add_error( |
|
502 | - esc_html__( |
|
503 | - 'In order to duplicate an event an Event ID is required. None was given.', |
|
504 | - 'event_espresso' |
|
505 | - ), |
|
506 | - __FILE__, |
|
507 | - __FUNCTION__, |
|
508 | - __LINE__ |
|
509 | - ); |
|
510 | - $this->_redirect_after_action(false, '', '', array(), true); |
|
511 | - return; |
|
512 | - } |
|
513 | - //k we've got EVT_ID so let's use that to get the event we'll duplicate |
|
514 | - $orig_event = EEM_Event::instance()->get_one_by_ID($this->_req_data['EVT_ID']); |
|
515 | - if (! $orig_event instanceof EE_Event) { |
|
516 | - throw new EE_Error( |
|
517 | - sprintf( |
|
518 | - esc_html__('An EE_Event object could not be retrieved for the given ID (%s)', 'event_espresso'), |
|
519 | - $this->_req_data['EVT_ID'] |
|
520 | - ) |
|
521 | - ); |
|
522 | - } |
|
523 | - //k now let's clone the $orig_event before getting relations |
|
524 | - $new_event = clone $orig_event; |
|
525 | - //original datetimes |
|
526 | - $orig_datetimes = $orig_event->get_many_related('Datetime'); |
|
527 | - //other original relations |
|
528 | - $orig_ven = $orig_event->get_many_related('Venue'); |
|
529 | - //reset the ID and modify other details to make it clear this is a dupe |
|
530 | - $new_event->set('EVT_ID', 0); |
|
531 | - $new_name = $new_event->name() . ' ' . esc_html__('**DUPLICATE**', 'event_espresso'); |
|
532 | - $new_event->set('EVT_name', $new_name); |
|
533 | - $new_event->set( |
|
534 | - 'EVT_slug', |
|
535 | - wp_unique_post_slug( |
|
536 | - sanitize_title($orig_event->name()), |
|
537 | - 0, |
|
538 | - 'publish', |
|
539 | - 'espresso_events', |
|
540 | - 0 |
|
541 | - ) |
|
542 | - ); |
|
543 | - $new_event->set('status', 'draft'); |
|
544 | - //duplicate discussion settings |
|
545 | - $new_event->set('comment_status', $orig_event->get('comment_status')); |
|
546 | - $new_event->set('ping_status', $orig_event->get('ping_status')); |
|
547 | - //save the new event |
|
548 | - $new_event->save(); |
|
549 | - //venues |
|
550 | - foreach ($orig_ven as $ven) { |
|
551 | - $new_event->_add_relation_to($ven, 'Venue'); |
|
552 | - } |
|
553 | - $new_event->save(); |
|
554 | - //now we need to get the question group relations and handle that |
|
555 | - //first primary question groups |
|
556 | - $orig_primary_qgs = $orig_event->get_many_related( |
|
557 | - 'Question_Group', |
|
558 | - array(array('Event_Question_Group.EQG_primary' => 1)) |
|
559 | - ); |
|
560 | - if (! empty($orig_primary_qgs)) { |
|
561 | - foreach ($orig_primary_qgs as $id => $obj) { |
|
562 | - if ($obj instanceof EE_Question_Group) { |
|
563 | - $new_event->_add_relation_to($obj, 'Question_Group', array('EQG_primary' => 1)); |
|
564 | - } |
|
565 | - } |
|
566 | - } |
|
567 | - //next additional attendee question groups |
|
568 | - $orig_additional_qgs = $orig_event->get_many_related( |
|
569 | - 'Question_Group', |
|
570 | - array(array('Event_Question_Group.EQG_primary' => 0)) |
|
571 | - ); |
|
572 | - if (! empty($orig_additional_qgs)) { |
|
573 | - foreach ($orig_additional_qgs as $id => $obj) { |
|
574 | - if ($obj instanceof EE_Question_Group) { |
|
575 | - $new_event->_add_relation_to($obj, 'Question_Group', array('EQG_primary' => 0)); |
|
576 | - } |
|
577 | - } |
|
578 | - } |
|
579 | - |
|
580 | - $new_event->save(); |
|
581 | - |
|
582 | - //k now that we have the new event saved we can loop through the datetimes and start adding relations. |
|
583 | - $cloned_tickets = array(); |
|
584 | - foreach ($orig_datetimes as $orig_dtt) { |
|
585 | - if (! $orig_dtt instanceof EE_Datetime) { |
|
586 | - continue; |
|
587 | - } |
|
588 | - $new_dtt = clone $orig_dtt; |
|
589 | - $orig_tkts = $orig_dtt->tickets(); |
|
590 | - //save new dtt then add to event |
|
591 | - $new_dtt->set('DTT_ID', 0); |
|
592 | - $new_dtt->set('DTT_sold', 0); |
|
593 | - $new_dtt->set_reserved(0); |
|
594 | - $new_dtt->save(); |
|
595 | - $new_event->_add_relation_to($new_dtt, 'Datetime'); |
|
596 | - $new_event->save(); |
|
597 | - //now let's get the ticket relations setup. |
|
598 | - foreach ((array)$orig_tkts as $orig_tkt) { |
|
599 | - //it's possible a datetime will have no tickets so let's verify we HAVE a ticket first. |
|
600 | - if (! $orig_tkt instanceof EE_Ticket) { |
|
601 | - continue; |
|
602 | - } |
|
603 | - //is this ticket archived? If it is then let's skip |
|
604 | - if ($orig_tkt->get('TKT_deleted')) { |
|
605 | - continue; |
|
606 | - } |
|
607 | - // does this original ticket already exist in the clone_tickets cache? |
|
608 | - // If so we'll just use the new ticket from it. |
|
609 | - if (isset($cloned_tickets[$orig_tkt->ID()])) { |
|
610 | - $new_tkt = $cloned_tickets[$orig_tkt->ID()]; |
|
611 | - } else { |
|
612 | - $new_tkt = clone $orig_tkt; |
|
613 | - //get relations on the $orig_tkt that we need to setup. |
|
614 | - $orig_prices = $orig_tkt->prices(); |
|
615 | - $new_tkt->set('TKT_ID', 0); |
|
616 | - $new_tkt->set('TKT_sold', 0); |
|
617 | - $new_tkt->set('TKT_reserved', 0); |
|
618 | - $new_tkt->save(); //make sure new ticket has ID. |
|
619 | - //price relations on new ticket need to be setup. |
|
620 | - foreach ($orig_prices as $orig_price) { |
|
621 | - $new_price = clone $orig_price; |
|
622 | - $new_price->set('PRC_ID', 0); |
|
623 | - $new_price->save(); |
|
624 | - $new_tkt->_add_relation_to($new_price, 'Price'); |
|
625 | - $new_tkt->save(); |
|
626 | - } |
|
627 | - |
|
628 | - do_action( |
|
629 | - 'AHEE__Extend_Events_Admin_Page___duplicate_event__duplicate_ticket__after', |
|
630 | - $orig_tkt, |
|
631 | - $new_tkt, |
|
632 | - $orig_prices, |
|
633 | - $orig_event, |
|
634 | - $orig_dtt, |
|
635 | - $new_dtt |
|
636 | - ); |
|
637 | - } |
|
638 | - // k now we can add the new ticket as a relation to the new datetime |
|
639 | - // and make sure its added to our cached $cloned_tickets array |
|
640 | - // for use with later datetimes that have the same ticket. |
|
641 | - $new_dtt->_add_relation_to($new_tkt, 'Ticket'); |
|
642 | - $new_dtt->save(); |
|
643 | - $cloned_tickets[$orig_tkt->ID()] = $new_tkt; |
|
644 | - } |
|
645 | - } |
|
646 | - //clone taxonomy information |
|
647 | - $taxonomies_to_clone_with = apply_filters( |
|
648 | - 'FHEE__Extend_Events_Admin_Page___duplicate_event__taxonomies_to_clone', |
|
649 | - array('espresso_event_categories', 'espresso_event_type', 'post_tag') |
|
650 | - ); |
|
651 | - //get terms for original event (notice) |
|
652 | - $orig_terms = wp_get_object_terms($orig_event->ID(), $taxonomies_to_clone_with); |
|
653 | - //loop through terms and add them to new event. |
|
654 | - foreach ($orig_terms as $term) { |
|
655 | - wp_set_object_terms($new_event->ID(), $term->term_id, $term->taxonomy, true); |
|
656 | - } |
|
657 | - |
|
658 | - //duplicate other core WP_Post items for this event. |
|
659 | - //post thumbnail (feature image). |
|
660 | - $feature_image_id = get_post_thumbnail_id($orig_event->ID()); |
|
661 | - if ($feature_image_id) { |
|
662 | - update_post_meta($new_event->ID(), '_thumbnail_id', $feature_image_id); |
|
663 | - } |
|
664 | - |
|
665 | - //duplicate page_template setting |
|
666 | - $page_template = get_post_meta($orig_event->ID(), '_wp_page_template', true); |
|
667 | - if ($page_template) { |
|
668 | - update_post_meta($new_event->ID(), '_wp_page_template', $page_template); |
|
669 | - } |
|
670 | - |
|
671 | - do_action('AHEE__Extend_Events_Admin_Page___duplicate_event__after', $new_event, $orig_event); |
|
672 | - //now let's redirect to the edit page for this duplicated event if we have a new event id. |
|
673 | - if ($new_event->ID()) { |
|
674 | - $redirect_args = array( |
|
675 | - 'post' => $new_event->ID(), |
|
676 | - 'action' => 'edit', |
|
677 | - ); |
|
678 | - EE_Error::add_success( |
|
679 | - esc_html__( |
|
680 | - 'Event successfully duplicated. Please review the details below and make any necessary edits', |
|
681 | - 'event_espresso' |
|
682 | - ) |
|
683 | - ); |
|
684 | - } else { |
|
685 | - $redirect_args = array( |
|
686 | - 'action' => 'default', |
|
687 | - ); |
|
688 | - EE_Error::add_error( |
|
689 | - esc_html__('Not able to duplicate event. Something went wrong.', 'event_espresso'), |
|
690 | - __FILE__, |
|
691 | - __FUNCTION__, |
|
692 | - __LINE__ |
|
693 | - ); |
|
694 | - } |
|
695 | - $this->_redirect_after_action(false, '', '', $redirect_args, true); |
|
696 | - } |
|
697 | - |
|
698 | - |
|
699 | - /** |
|
700 | - * Generates output for the import page. |
|
701 | - * @throws DomainException |
|
702 | - */ |
|
703 | - protected function _import_page() |
|
704 | - { |
|
705 | - $title = esc_html__('Import', 'event_espresso'); |
|
706 | - $intro = esc_html__( |
|
707 | - 'If you have a previously exported Event Espresso 4 information in a Comma Separated Value (CSV) file format, you can upload the file here: ', |
|
708 | - 'event_espresso' |
|
709 | - ); |
|
710 | - $form_url = EVENTS_ADMIN_URL; |
|
711 | - $action = 'import_events'; |
|
712 | - $type = 'csv'; |
|
713 | - $this->_template_args['form'] = EE_Import::instance()->upload_form( |
|
714 | - $title, $intro, $form_url, $action, $type |
|
715 | - ); |
|
716 | - $this->_template_args['sample_file_link'] = EE_Admin_Page::add_query_args_and_nonce( |
|
717 | - array('action' => 'sample_export_file'), |
|
718 | - $this->_admin_base_url |
|
719 | - ); |
|
720 | - $content = EEH_Template::display_template( |
|
721 | - EVENTS_CAF_TEMPLATE_PATH . 'import_page.template.php', |
|
722 | - $this->_template_args, |
|
723 | - true |
|
724 | - ); |
|
725 | - $this->_template_args['admin_page_content'] = $content; |
|
726 | - $this->display_admin_page_with_sidebar(); |
|
727 | - } |
|
728 | - |
|
729 | - |
|
730 | - /** |
|
731 | - * _import_events |
|
732 | - * This handles displaying the screen and running imports for importing events. |
|
733 | - * |
|
734 | - * @return void |
|
735 | - */ |
|
736 | - protected function _import_events() |
|
737 | - { |
|
738 | - require_once(EE_CLASSES . 'EE_Import.class.php'); |
|
739 | - $success = EE_Import::instance()->import(); |
|
740 | - $this->_redirect_after_action($success, 'Import File', 'ran', array('action' => 'import_page'), true); |
|
741 | - } |
|
742 | - |
|
743 | - |
|
744 | - /** |
|
745 | - * _events_export |
|
746 | - * Will export all (or just the given event) to a Excel compatible file. |
|
747 | - * |
|
748 | - * @access protected |
|
749 | - * @return void |
|
750 | - */ |
|
751 | - protected function _events_export() |
|
752 | - { |
|
753 | - if (isset($this->_req_data['EVT_ID'])) { |
|
754 | - $event_ids = $this->_req_data['EVT_ID']; |
|
755 | - } elseif (isset($this->_req_data['EVT_IDs'])) { |
|
756 | - $event_ids = $this->_req_data['EVT_IDs']; |
|
757 | - } else { |
|
758 | - $event_ids = null; |
|
759 | - } |
|
760 | - //todo: I don't like doing this but it'll do until we modify EE_Export Class. |
|
761 | - $new_request_args = array( |
|
762 | - 'export' => 'report', |
|
763 | - 'action' => 'all_event_data', |
|
764 | - 'EVT_ID' => $event_ids, |
|
765 | - ); |
|
766 | - $this->_req_data = array_merge($this->_req_data, $new_request_args); |
|
767 | - if (is_readable(EE_CLASSES . 'EE_Export.class.php')) { |
|
768 | - require_once(EE_CLASSES . 'EE_Export.class.php'); |
|
769 | - $EE_Export = EE_Export::instance($this->_req_data); |
|
770 | - $EE_Export->export(); |
|
771 | - } |
|
772 | - } |
|
773 | - |
|
774 | - |
|
775 | - /** |
|
776 | - * handle category exports() |
|
777 | - * |
|
778 | - * @return void |
|
779 | - */ |
|
780 | - protected function _categories_export() |
|
781 | - { |
|
782 | - //todo: I don't like doing this but it'll do until we modify EE_Export Class. |
|
783 | - $new_request_args = array( |
|
784 | - 'export' => 'report', |
|
785 | - 'action' => 'categories', |
|
786 | - 'category_ids' => $this->_req_data['EVT_CAT_ID'], |
|
787 | - ); |
|
788 | - $this->_req_data = array_merge($this->_req_data, $new_request_args); |
|
789 | - if (is_readable(EE_CLASSES . 'EE_Export.class.php')) { |
|
790 | - require_once(EE_CLASSES . 'EE_Export.class.php'); |
|
791 | - $EE_Export = EE_Export::instance($this->_req_data); |
|
792 | - $EE_Export->export(); |
|
793 | - } |
|
794 | - } |
|
795 | - |
|
796 | - |
|
797 | - /** |
|
798 | - * Creates a sample CSV file for importing |
|
799 | - */ |
|
800 | - protected function _sample_export_file() |
|
801 | - { |
|
802 | - // require_once(EE_CLASSES . 'EE_Export.class.php'); |
|
803 | - EE_Export::instance()->export_sample(); |
|
804 | - } |
|
805 | - |
|
806 | - |
|
807 | - /************* Template Settings *************/ |
|
808 | - /** |
|
809 | - * Generates template settings page output |
|
810 | - * @throws DomainException |
|
811 | - * @throws EE_Error |
|
812 | - */ |
|
813 | - protected function _template_settings() |
|
814 | - { |
|
815 | - $this->_template_args['values'] = $this->_yes_no_values; |
|
816 | - /** |
|
817 | - * Note leaving this filter in for backward compatibility this was moved in 4.6.x |
|
818 | - * from General_Settings_Admin_Page to here. |
|
819 | - */ |
|
820 | - $this->_template_args = apply_filters( |
|
821 | - 'FHEE__General_Settings_Admin_Page__template_settings__template_args', |
|
822 | - $this->_template_args |
|
823 | - ); |
|
824 | - $this->_set_add_edit_form_tags('update_template_settings'); |
|
825 | - $this->_set_publish_post_box_vars(null, false, false, null, false); |
|
826 | - $this->_template_args['admin_page_content'] = EEH_Template::display_template( |
|
827 | - EVENTS_CAF_TEMPLATE_PATH . 'template_settings.template.php', |
|
828 | - $this->_template_args, |
|
829 | - true |
|
830 | - ); |
|
831 | - $this->display_admin_page_with_sidebar(); |
|
832 | - } |
|
833 | - |
|
834 | - |
|
835 | - /** |
|
836 | - * Handler for updating template settings. |
|
837 | - */ |
|
838 | - protected function _update_template_settings() |
|
839 | - { |
|
840 | - /** |
|
841 | - * Note leaving this filter in for backward compatibility this was moved in 4.6.x |
|
842 | - * from General_Settings_Admin_Page to here. |
|
843 | - */ |
|
844 | - EE_Registry::instance()->CFG->template_settings = apply_filters( |
|
845 | - 'FHEE__General_Settings_Admin_Page__update_template_settings__data', |
|
846 | - EE_Registry::instance()->CFG->template_settings, |
|
847 | - $this->_req_data |
|
848 | - ); |
|
849 | - //update custom post type slugs and detect if we need to flush rewrite rules |
|
850 | - $old_slug = EE_Registry::instance()->CFG->core->event_cpt_slug; |
|
851 | - EE_Registry::instance()->CFG->core->event_cpt_slug = empty($this->_req_data['event_cpt_slug']) |
|
852 | - ? EE_Registry::instance()->CFG->core->event_cpt_slug |
|
853 | - : sanitize_title_with_dashes($this->_req_data['event_cpt_slug']); |
|
854 | - $what = 'Template Settings'; |
|
855 | - $success = $this->_update_espresso_configuration( |
|
856 | - $what, |
|
857 | - EE_Registry::instance()->CFG->template_settings, |
|
858 | - __FILE__, |
|
859 | - __FUNCTION__, |
|
860 | - __LINE__ |
|
861 | - ); |
|
862 | - if (EE_Registry::instance()->CFG->core->event_cpt_slug != $old_slug) { |
|
863 | - update_option('ee_flush_rewrite_rules', true); |
|
864 | - } |
|
865 | - $this->_redirect_after_action($success, $what, 'updated', array('action' => 'template_settings')); |
|
866 | - } |
|
867 | - |
|
868 | - |
|
869 | - /** |
|
870 | - * _premium_event_editor_meta_boxes |
|
871 | - * add all metaboxes related to the event_editor |
|
872 | - * |
|
873 | - * @access protected |
|
874 | - * @return void |
|
875 | - * @throws EE_Error |
|
876 | - */ |
|
877 | - protected function _premium_event_editor_meta_boxes() |
|
878 | - { |
|
879 | - $this->verify_cpt_object(); |
|
880 | - add_meta_box( |
|
881 | - 'espresso_event_editor_event_options', |
|
882 | - esc_html__('Event Registration Options', 'event_espresso'), |
|
883 | - array($this, 'registration_options_meta_box'), |
|
884 | - $this->page_slug, |
|
885 | - 'side', |
|
886 | - 'core' |
|
887 | - ); |
|
888 | - } |
|
889 | - |
|
890 | - |
|
891 | - /** |
|
892 | - * override caf metabox |
|
893 | - * |
|
894 | - * @return void |
|
895 | - * @throws DomainException |
|
896 | - */ |
|
897 | - public function registration_options_meta_box() |
|
898 | - { |
|
899 | - $yes_no_values = array( |
|
900 | - array('id' => true, 'text' => esc_html__('Yes', 'event_espresso')), |
|
901 | - array('id' => false, 'text' => esc_html__('No', 'event_espresso')), |
|
902 | - ); |
|
903 | - $default_reg_status_values = EEM_Registration::reg_status_array( |
|
904 | - array( |
|
905 | - EEM_Registration::status_id_cancelled, |
|
906 | - EEM_Registration::status_id_declined, |
|
907 | - EEM_Registration::status_id_incomplete, |
|
908 | - EEM_Registration::status_id_wait_list, |
|
909 | - ), |
|
910 | - true |
|
911 | - ); |
|
912 | - $template_args['active_status'] = $this->_cpt_model_obj->pretty_active_status(false); |
|
913 | - $template_args['_event'] = $this->_cpt_model_obj; |
|
914 | - $template_args['additional_limit'] = $this->_cpt_model_obj->additional_limit(); |
|
915 | - $template_args['default_registration_status'] = EEH_Form_Fields::select_input( |
|
916 | - 'default_reg_status', |
|
917 | - $default_reg_status_values, |
|
918 | - $this->_cpt_model_obj->default_registration_status() |
|
919 | - ); |
|
920 | - $template_args['display_description'] = EEH_Form_Fields::select_input( |
|
921 | - 'display_desc', |
|
922 | - $yes_no_values, |
|
923 | - $this->_cpt_model_obj->display_description() |
|
924 | - ); |
|
925 | - $template_args['display_ticket_selector'] = EEH_Form_Fields::select_input( |
|
926 | - 'display_ticket_selector', |
|
927 | - $yes_no_values, |
|
928 | - $this->_cpt_model_obj->display_ticket_selector(), |
|
929 | - '', |
|
930 | - '', |
|
931 | - false |
|
932 | - ); |
|
933 | - $template_args['EVT_default_registration_status'] = EEH_Form_Fields::select_input( |
|
934 | - 'EVT_default_registration_status', |
|
935 | - $default_reg_status_values, |
|
936 | - $this->_cpt_model_obj->default_registration_status() |
|
937 | - ); |
|
938 | - $template_args['additional_registration_options'] = apply_filters( |
|
939 | - 'FHEE__Events_Admin_Page__registration_options_meta_box__additional_registration_options', |
|
940 | - '', |
|
941 | - $template_args, |
|
942 | - $yes_no_values, |
|
943 | - $default_reg_status_values |
|
944 | - ); |
|
945 | - EEH_Template::display_template( |
|
946 | - EVENTS_CAF_TEMPLATE_PATH . 'event_registration_options.template.php', |
|
947 | - $template_args |
|
948 | - ); |
|
949 | - } |
|
950 | - |
|
951 | - |
|
952 | - |
|
953 | - /** |
|
954 | - * wp_list_table_mods for caf |
|
955 | - * ============================ |
|
956 | - */ |
|
957 | - /** |
|
958 | - * hook into list table filters and provide filters for caffeinated list table |
|
959 | - * |
|
960 | - * @param array $old_filters any existing filters present |
|
961 | - * @param array $list_table_obj the list table object |
|
962 | - * @return array new filters |
|
963 | - */ |
|
964 | - public function list_table_filters($old_filters, $list_table_obj) |
|
965 | - { |
|
966 | - $filters = array(); |
|
967 | - //first month/year filters |
|
968 | - $filters[] = $this->espresso_event_months_dropdown(); |
|
969 | - $status = isset($this->_req_data['status']) ? $this->_req_data['status'] : null; |
|
970 | - //active status dropdown |
|
971 | - if ($status !== 'draft') { |
|
972 | - $filters[] = $this->active_status_dropdown( |
|
973 | - isset($this->_req_data['active_status']) ? $this->_req_data['active_status'] : '' |
|
974 | - ); |
|
975 | - } |
|
976 | - //category filter |
|
977 | - $filters[] = $this->category_dropdown(); |
|
978 | - return array_merge($old_filters, $filters); |
|
979 | - } |
|
980 | - |
|
981 | - |
|
982 | - /** |
|
983 | - * espresso_event_months_dropdown |
|
984 | - * |
|
985 | - * @access public |
|
986 | - * @return string dropdown listing month/year selections for events. |
|
987 | - */ |
|
988 | - public function espresso_event_months_dropdown() |
|
989 | - { |
|
990 | - // what we need to do is get all PRIMARY datetimes for all events to filter on. |
|
991 | - // Note we need to include any other filters that are set! |
|
992 | - $status = isset($this->_req_data['status']) ? $this->_req_data['status'] : null; |
|
993 | - //categories? |
|
994 | - $category = isset($this->_req_data['EVT_CAT']) && $this->_req_data['EVT_CAT'] > 0 |
|
995 | - ? $this->_req_data['EVT_CAT'] |
|
996 | - : null; |
|
997 | - //active status? |
|
998 | - $active_status = isset($this->_req_data['active_status']) ? $this->_req_data['active_status'] : null; |
|
999 | - $cur_date = isset($this->_req_data['month_range']) ? $this->_req_data['month_range'] : ''; |
|
1000 | - return EEH_Form_Fields::generate_event_months_dropdown($cur_date, $status, $category, $active_status); |
|
1001 | - } |
|
1002 | - |
|
1003 | - |
|
1004 | - /** |
|
1005 | - * returns a list of "active" statuses on the event |
|
1006 | - * |
|
1007 | - * @param string $current_value whatever the current active status is |
|
1008 | - * @return string |
|
1009 | - */ |
|
1010 | - public function active_status_dropdown($current_value = '') |
|
1011 | - { |
|
1012 | - $select_name = 'active_status'; |
|
1013 | - $values = array( |
|
1014 | - 'none' => esc_html__('Show Active/Inactive', 'event_espresso'), |
|
1015 | - 'active' => esc_html__('Active', 'event_espresso'), |
|
1016 | - 'upcoming' => esc_html__('Upcoming', 'event_espresso'), |
|
1017 | - 'expired' => esc_html__('Expired', 'event_espresso'), |
|
1018 | - 'inactive' => esc_html__('Inactive', 'event_espresso'), |
|
1019 | - ); |
|
1020 | - $id = 'id="espresso-active-status-dropdown-filter"'; |
|
1021 | - $class = 'wide'; |
|
1022 | - return EEH_Form_Fields::select_input($select_name, $values, $current_value, $id, $class); |
|
1023 | - } |
|
1024 | - |
|
1025 | - |
|
1026 | - /** |
|
1027 | - * output a dropdown of the categories for the category filter on the event admin list table |
|
1028 | - * |
|
1029 | - * @access public |
|
1030 | - * @return string html |
|
1031 | - */ |
|
1032 | - public function category_dropdown() |
|
1033 | - { |
|
1034 | - $cur_cat = isset($this->_req_data['EVT_CAT']) ? $this->_req_data['EVT_CAT'] : -1; |
|
1035 | - return EEH_Form_Fields::generate_event_category_dropdown($cur_cat); |
|
1036 | - } |
|
1037 | - |
|
1038 | - |
|
1039 | - /** |
|
1040 | - * get total number of events today |
|
1041 | - * |
|
1042 | - * @access public |
|
1043 | - * @return int |
|
1044 | - * @throws EE_Error |
|
1045 | - */ |
|
1046 | - public function total_events_today() |
|
1047 | - { |
|
1048 | - $start = EEM_Datetime::instance()->convert_datetime_for_query( |
|
1049 | - 'DTT_EVT_start', |
|
1050 | - date('Y-m-d') . ' 00:00:00', |
|
1051 | - 'Y-m-d H:i:s', |
|
1052 | - 'UTC' |
|
1053 | - ); |
|
1054 | - $end = EEM_Datetime::instance()->convert_datetime_for_query( |
|
1055 | - 'DTT_EVT_start', |
|
1056 | - date('Y-m-d') . ' 23:59:59', |
|
1057 | - 'Y-m-d H:i:s', |
|
1058 | - 'UTC' |
|
1059 | - ); |
|
1060 | - $where = array( |
|
1061 | - 'Datetime.DTT_EVT_start' => array('BETWEEN', array($start, $end)), |
|
1062 | - ); |
|
1063 | - $count = EEM_Event::instance()->count(array($where, 'caps' => 'read_admin'), 'EVT_ID', true); |
|
1064 | - return $count; |
|
1065 | - } |
|
1066 | - |
|
1067 | - |
|
1068 | - /** |
|
1069 | - * get total number of events this month |
|
1070 | - * |
|
1071 | - * @access public |
|
1072 | - * @return int |
|
1073 | - * @throws EE_Error |
|
1074 | - */ |
|
1075 | - public function total_events_this_month() |
|
1076 | - { |
|
1077 | - //Dates |
|
1078 | - $this_year_r = date('Y'); |
|
1079 | - $this_month_r = date('m'); |
|
1080 | - $days_this_month = date('t'); |
|
1081 | - $start = EEM_Datetime::instance()->convert_datetime_for_query( |
|
1082 | - 'DTT_EVT_start', |
|
1083 | - $this_year_r . '-' . $this_month_r . '-01 00:00:00', |
|
1084 | - 'Y-m-d H:i:s', |
|
1085 | - 'UTC' |
|
1086 | - ); |
|
1087 | - $end = EEM_Datetime::instance()->convert_datetime_for_query( |
|
1088 | - 'DTT_EVT_start', |
|
1089 | - $this_year_r . '-' . $this_month_r . '-' . $days_this_month . ' 23:59:59', |
|
1090 | - 'Y-m-d H:i:s', |
|
1091 | - 'UTC' |
|
1092 | - ); |
|
1093 | - $where = array( |
|
1094 | - 'Datetime.DTT_EVT_start' => array('BETWEEN', array($start, $end)), |
|
1095 | - ); |
|
1096 | - $count = EEM_Event::instance()->count(array($where, 'caps' => 'read_admin'), 'EVT_ID', true); |
|
1097 | - return $count; |
|
1098 | - } |
|
1099 | - |
|
1100 | - |
|
1101 | - /** DEFAULT TICKETS STUFF **/ |
|
1102 | - |
|
1103 | - /** |
|
1104 | - * Output default tickets list table view. |
|
1105 | - */ |
|
1106 | - public function _tickets_overview_list_table() |
|
1107 | - { |
|
1108 | - $this->_search_btn_label = esc_html__('Tickets', 'event_espresso'); |
|
1109 | - $this->display_admin_list_table_page_with_no_sidebar(); |
|
1110 | - } |
|
1111 | - |
|
1112 | - |
|
1113 | - /** |
|
1114 | - * @param int $per_page |
|
1115 | - * @param bool $count |
|
1116 | - * @param bool $trashed |
|
1117 | - * @return \EE_Soft_Delete_Base_Class[]|int |
|
1118 | - */ |
|
1119 | - public function get_default_tickets($per_page = 10, $count = false, $trashed = false) |
|
1120 | - { |
|
1121 | - $orderby = empty($this->_req_data['orderby']) ? 'TKT_name' : $this->_req_data['orderby']; |
|
1122 | - $order = empty($this->_req_data['order']) ? 'ASC' : $this->_req_data['order']; |
|
1123 | - switch ($orderby) { |
|
1124 | - case 'TKT_name': |
|
1125 | - $orderby = array('TKT_name' => $order); |
|
1126 | - break; |
|
1127 | - case 'TKT_price': |
|
1128 | - $orderby = array('TKT_price' => $order); |
|
1129 | - break; |
|
1130 | - case 'TKT_uses': |
|
1131 | - $orderby = array('TKT_uses' => $order); |
|
1132 | - break; |
|
1133 | - case 'TKT_min': |
|
1134 | - $orderby = array('TKT_min' => $order); |
|
1135 | - break; |
|
1136 | - case 'TKT_max': |
|
1137 | - $orderby = array('TKT_max' => $order); |
|
1138 | - break; |
|
1139 | - case 'TKT_qty': |
|
1140 | - $orderby = array('TKT_qty' => $order); |
|
1141 | - break; |
|
1142 | - } |
|
1143 | - $current_page = isset($this->_req_data['paged']) && ! empty($this->_req_data['paged']) |
|
1144 | - ? $this->_req_data['paged'] |
|
1145 | - : 1; |
|
1146 | - $per_page = isset($this->_req_data['perpage']) && ! empty($this->_req_data['perpage']) |
|
1147 | - ? $this->_req_data['perpage'] |
|
1148 | - : $per_page; |
|
1149 | - $_where = array( |
|
1150 | - 'TKT_is_default' => 1, |
|
1151 | - 'TKT_deleted' => $trashed, |
|
1152 | - ); |
|
1153 | - $offset = ($current_page - 1) * $per_page; |
|
1154 | - $limit = array($offset, $per_page); |
|
1155 | - if (isset($this->_req_data['s'])) { |
|
1156 | - $sstr = '%' . $this->_req_data['s'] . '%'; |
|
1157 | - $_where['OR'] = array( |
|
1158 | - 'TKT_name' => array('LIKE', $sstr), |
|
1159 | - 'TKT_description' => array('LIKE', $sstr), |
|
1160 | - ); |
|
1161 | - } |
|
1162 | - $query_params = array( |
|
1163 | - $_where, |
|
1164 | - 'order_by' => $orderby, |
|
1165 | - 'limit' => $limit, |
|
1166 | - 'group_by' => 'TKT_ID', |
|
1167 | - ); |
|
1168 | - if ($count) { |
|
1169 | - return EEM_Ticket::instance()->count_deleted_and_undeleted(array($_where)); |
|
1170 | - } else { |
|
1171 | - return EEM_Ticket::instance()->get_all_deleted_and_undeleted($query_params); |
|
1172 | - } |
|
1173 | - } |
|
1174 | - |
|
1175 | - |
|
1176 | - /** |
|
1177 | - * @param bool $trash |
|
1178 | - * @throws EE_Error |
|
1179 | - */ |
|
1180 | - protected function _trash_or_restore_ticket($trash = false) |
|
1181 | - { |
|
1182 | - $success = 1; |
|
1183 | - $TKT = EEM_Ticket::instance(); |
|
1184 | - //checkboxes? |
|
1185 | - if (! empty($this->_req_data['checkbox']) && is_array($this->_req_data['checkbox'])) { |
|
1186 | - //if array has more than one element then success message should be plural |
|
1187 | - $success = count($this->_req_data['checkbox']) > 1 ? 2 : 1; |
|
1188 | - //cycle thru the boxes |
|
1189 | - while (list($TKT_ID, $value) = each($this->_req_data['checkbox'])) { |
|
1190 | - if ($trash) { |
|
1191 | - if (! $TKT->delete_by_ID($TKT_ID)) { |
|
1192 | - $success = 0; |
|
1193 | - } |
|
1194 | - } else { |
|
1195 | - if (! $TKT->restore_by_ID($TKT_ID)) { |
|
1196 | - $success = 0; |
|
1197 | - } |
|
1198 | - } |
|
1199 | - } |
|
1200 | - } else { |
|
1201 | - //grab single id and trash |
|
1202 | - $TKT_ID = absint($this->_req_data['TKT_ID']); |
|
1203 | - if ($trash) { |
|
1204 | - if (! $TKT->delete_by_ID($TKT_ID)) { |
|
1205 | - $success = 0; |
|
1206 | - } |
|
1207 | - } else { |
|
1208 | - if (! $TKT->restore_by_ID($TKT_ID)) { |
|
1209 | - $success = 0; |
|
1210 | - } |
|
1211 | - } |
|
1212 | - } |
|
1213 | - $action_desc = $trash ? 'moved to the trash' : 'restored'; |
|
1214 | - $query_args = array( |
|
1215 | - 'action' => 'ticket_list_table', |
|
1216 | - 'status' => $trash ? '' : 'trashed', |
|
1217 | - ); |
|
1218 | - $this->_redirect_after_action($success, 'Tickets', $action_desc, $query_args); |
|
1219 | - } |
|
1220 | - |
|
1221 | - |
|
1222 | - /** |
|
1223 | - * Handles trashing default ticket. |
|
1224 | - */ |
|
1225 | - protected function _delete_ticket() |
|
1226 | - { |
|
1227 | - $success = 1; |
|
1228 | - //checkboxes? |
|
1229 | - if (! empty($this->_req_data['checkbox']) && is_array($this->_req_data['checkbox'])) { |
|
1230 | - //if array has more than one element then success message should be plural |
|
1231 | - $success = count($this->_req_data['checkbox']) > 1 ? 2 : 1; |
|
1232 | - //cycle thru the boxes |
|
1233 | - while (list($TKT_ID, $value) = each($this->_req_data['checkbox'])) { |
|
1234 | - //delete |
|
1235 | - if (! $this->_delete_the_ticket($TKT_ID)) { |
|
1236 | - $success = 0; |
|
1237 | - } |
|
1238 | - } |
|
1239 | - } else { |
|
1240 | - //grab single id and trash |
|
1241 | - $TKT_ID = absint($this->_req_data['TKT_ID']); |
|
1242 | - if (! $this->_delete_the_ticket($TKT_ID)) { |
|
1243 | - $success = 0; |
|
1244 | - } |
|
1245 | - } |
|
1246 | - $action_desc = 'deleted'; |
|
1247 | - $query_args = array( |
|
1248 | - 'action' => 'ticket_list_table', |
|
1249 | - 'status' => 'trashed', |
|
1250 | - ); |
|
1251 | - //fail safe. If the default ticket count === 1 then we need to redirect to event overview. |
|
1252 | - if (EEM_Ticket::instance()->count_deleted_and_undeleted( |
|
1253 | - array(array('TKT_is_default' => 1)), |
|
1254 | - 'TKT_ID', |
|
1255 | - true |
|
1256 | - ) |
|
1257 | - ) { |
|
1258 | - $query_args = array(); |
|
1259 | - } |
|
1260 | - $this->_redirect_after_action($success, 'Tickets', $action_desc, $query_args); |
|
1261 | - } |
|
1262 | - |
|
1263 | - |
|
1264 | - /** |
|
1265 | - * @param int $TKT_ID |
|
1266 | - * @return bool|int |
|
1267 | - * @throws EE_Error |
|
1268 | - */ |
|
1269 | - protected function _delete_the_ticket($TKT_ID) |
|
1270 | - { |
|
1271 | - $tkt = EEM_Ticket::instance()->get_one_by_ID($TKT_ID); |
|
1272 | - $tkt->_remove_relations('Datetime'); |
|
1273 | - //delete all related prices first |
|
1274 | - $tkt->delete_related_permanently('Price'); |
|
1275 | - return $tkt->delete_permanently(); |
|
1276 | - } |
|
17 | + /** |
|
18 | + * Extend_Events_Admin_Page constructor. |
|
19 | + * |
|
20 | + * @param bool $routing |
|
21 | + */ |
|
22 | + public function __construct($routing = true) |
|
23 | + { |
|
24 | + parent::__construct($routing); |
|
25 | + if (! defined('EVENTS_CAF_TEMPLATE_PATH')) { |
|
26 | + define('EVENTS_CAF_TEMPLATE_PATH', EE_CORE_CAF_ADMIN_EXTEND . 'events/templates/'); |
|
27 | + define('EVENTS_CAF_ASSETS', EE_CORE_CAF_ADMIN_EXTEND . 'events/assets/'); |
|
28 | + define('EVENTS_CAF_ASSETS_URL', EE_CORE_CAF_ADMIN_EXTEND_URL . 'events/assets/'); |
|
29 | + } |
|
30 | + } |
|
31 | + |
|
32 | + |
|
33 | + /** |
|
34 | + * Sets routes. |
|
35 | + */ |
|
36 | + protected function _extend_page_config() |
|
37 | + { |
|
38 | + $this->_admin_base_path = EE_CORE_CAF_ADMIN_EXTEND . 'events'; |
|
39 | + //is there a evt_id in the request? |
|
40 | + $evt_id = ! empty($this->_req_data['EVT_ID']) && ! is_array($this->_req_data['EVT_ID']) |
|
41 | + ? $this->_req_data['EVT_ID'] |
|
42 | + : 0; |
|
43 | + $evt_id = ! empty($this->_req_data['post']) ? $this->_req_data['post'] : $evt_id; |
|
44 | + //tkt_id? |
|
45 | + $tkt_id = ! empty($this->_req_data['TKT_ID']) && ! is_array($this->_req_data['TKT_ID']) |
|
46 | + ? $this->_req_data['TKT_ID'] |
|
47 | + : 0; |
|
48 | + $new_page_routes = array( |
|
49 | + 'duplicate_event' => array( |
|
50 | + 'func' => '_duplicate_event', |
|
51 | + 'capability' => 'ee_edit_event', |
|
52 | + 'obj_id' => $evt_id, |
|
53 | + 'noheader' => true, |
|
54 | + ), |
|
55 | + 'ticket_list_table' => array( |
|
56 | + 'func' => '_tickets_overview_list_table', |
|
57 | + 'capability' => 'ee_read_default_tickets', |
|
58 | + ), |
|
59 | + 'trash_ticket' => array( |
|
60 | + 'func' => '_trash_or_restore_ticket', |
|
61 | + 'capability' => 'ee_delete_default_ticket', |
|
62 | + 'obj_id' => $tkt_id, |
|
63 | + 'noheader' => true, |
|
64 | + 'args' => array('trash' => true), |
|
65 | + ), |
|
66 | + 'trash_tickets' => array( |
|
67 | + 'func' => '_trash_or_restore_ticket', |
|
68 | + 'capability' => 'ee_delete_default_tickets', |
|
69 | + 'noheader' => true, |
|
70 | + 'args' => array('trash' => true), |
|
71 | + ), |
|
72 | + 'restore_ticket' => array( |
|
73 | + 'func' => '_trash_or_restore_ticket', |
|
74 | + 'capability' => 'ee_delete_default_ticket', |
|
75 | + 'obj_id' => $tkt_id, |
|
76 | + 'noheader' => true, |
|
77 | + ), |
|
78 | + 'restore_tickets' => array( |
|
79 | + 'func' => '_trash_or_restore_ticket', |
|
80 | + 'capability' => 'ee_delete_default_tickets', |
|
81 | + 'noheader' => true, |
|
82 | + ), |
|
83 | + 'delete_ticket' => array( |
|
84 | + 'func' => '_delete_ticket', |
|
85 | + 'capability' => 'ee_delete_default_ticket', |
|
86 | + 'obj_id' => $tkt_id, |
|
87 | + 'noheader' => true, |
|
88 | + ), |
|
89 | + 'delete_tickets' => array( |
|
90 | + 'func' => '_delete_ticket', |
|
91 | + 'capability' => 'ee_delete_default_tickets', |
|
92 | + 'noheader' => true, |
|
93 | + ), |
|
94 | + 'import_page' => array( |
|
95 | + 'func' => '_import_page', |
|
96 | + 'capability' => 'import', |
|
97 | + ), |
|
98 | + 'import' => array( |
|
99 | + 'func' => '_import_events', |
|
100 | + 'capability' => 'import', |
|
101 | + 'noheader' => true, |
|
102 | + ), |
|
103 | + 'import_events' => array( |
|
104 | + 'func' => '_import_events', |
|
105 | + 'capability' => 'import', |
|
106 | + 'noheader' => true, |
|
107 | + ), |
|
108 | + 'export_events' => array( |
|
109 | + 'func' => '_events_export', |
|
110 | + 'capability' => 'export', |
|
111 | + 'noheader' => true, |
|
112 | + ), |
|
113 | + 'export_categories' => array( |
|
114 | + 'func' => '_categories_export', |
|
115 | + 'capability' => 'export', |
|
116 | + 'noheader' => true, |
|
117 | + ), |
|
118 | + 'sample_export_file' => array( |
|
119 | + 'func' => '_sample_export_file', |
|
120 | + 'capability' => 'export', |
|
121 | + 'noheader' => true, |
|
122 | + ), |
|
123 | + 'update_template_settings' => array( |
|
124 | + 'func' => '_update_template_settings', |
|
125 | + 'capability' => 'manage_options', |
|
126 | + 'noheader' => true, |
|
127 | + ), |
|
128 | + ); |
|
129 | + $this->_page_routes = array_merge($this->_page_routes, $new_page_routes); |
|
130 | + //partial route/config override |
|
131 | + $this->_page_config['import_events']['metaboxes'] = $this->_default_espresso_metaboxes; |
|
132 | + $this->_page_config['create_new']['metaboxes'][] = '_premium_event_editor_meta_boxes'; |
|
133 | + $this->_page_config['create_new']['qtips'][] = 'EE_Event_Editor_Tips'; |
|
134 | + $this->_page_config['edit']['qtips'][] = 'EE_Event_Editor_Tips'; |
|
135 | + $this->_page_config['edit']['metaboxes'][] = '_premium_event_editor_meta_boxes'; |
|
136 | + $this->_page_config['default']['list_table'] = 'Extend_Events_Admin_List_Table'; |
|
137 | + //add tickets tab but only if there are more than one default ticket! |
|
138 | + $tkt_count = EEM_Ticket::instance()->count_deleted_and_undeleted( |
|
139 | + array(array('TKT_is_default' => 1)), |
|
140 | + 'TKT_ID', |
|
141 | + true |
|
142 | + ); |
|
143 | + if ($tkt_count > 1) { |
|
144 | + $new_page_config = array( |
|
145 | + 'ticket_list_table' => array( |
|
146 | + 'nav' => array( |
|
147 | + 'label' => esc_html__('Default Tickets', 'event_espresso'), |
|
148 | + 'order' => 60, |
|
149 | + ), |
|
150 | + 'list_table' => 'Tickets_List_Table', |
|
151 | + 'require_nonce' => false, |
|
152 | + ), |
|
153 | + ); |
|
154 | + } |
|
155 | + //template settings |
|
156 | + $new_page_config['template_settings'] = array( |
|
157 | + 'nav' => array( |
|
158 | + 'label' => esc_html__('Templates', 'event_espresso'), |
|
159 | + 'order' => 30, |
|
160 | + ), |
|
161 | + 'metaboxes' => array_merge($this->_default_espresso_metaboxes, array('_publish_post_box')), |
|
162 | + 'help_tabs' => array( |
|
163 | + 'general_settings_templates_help_tab' => array( |
|
164 | + 'title' => esc_html__('Templates', 'event_espresso'), |
|
165 | + 'filename' => 'general_settings_templates', |
|
166 | + ), |
|
167 | + ), |
|
168 | + 'help_tour' => array('Templates_Help_Tour'), |
|
169 | + 'require_nonce' => false, |
|
170 | + ); |
|
171 | + $this->_page_config = array_merge($this->_page_config, $new_page_config); |
|
172 | + //add filters and actions |
|
173 | + //modifying _views |
|
174 | + add_filter( |
|
175 | + 'FHEE_event_datetime_metabox_add_additional_date_time_template', |
|
176 | + array($this, 'add_additional_datetime_button'), |
|
177 | + 10, |
|
178 | + 2 |
|
179 | + ); |
|
180 | + add_filter( |
|
181 | + 'FHEE_event_datetime_metabox_clone_button_template', |
|
182 | + array($this, 'add_datetime_clone_button'), |
|
183 | + 10, |
|
184 | + 2 |
|
185 | + ); |
|
186 | + add_filter( |
|
187 | + 'FHEE_event_datetime_metabox_timezones_template', |
|
188 | + array($this, 'datetime_timezones_template'), |
|
189 | + 10, |
|
190 | + 2 |
|
191 | + ); |
|
192 | + //filters for event list table |
|
193 | + add_filter('FHEE__Extend_Events_Admin_List_Table__filters', array($this, 'list_table_filters'), 10, 2); |
|
194 | + add_filter( |
|
195 | + 'FHEE__Events_Admin_List_Table__column_actions__action_links', |
|
196 | + array($this, 'extra_list_table_actions'), |
|
197 | + 10, |
|
198 | + 2 |
|
199 | + ); |
|
200 | + //legend item |
|
201 | + add_filter('FHEE__Events_Admin_Page___event_legend_items__items', array($this, 'additional_legend_items')); |
|
202 | + add_action('admin_init', array($this, 'admin_init')); |
|
203 | + //heartbeat stuff |
|
204 | + add_filter('heartbeat_received', array($this, 'heartbeat_response'), 10, 2); |
|
205 | + } |
|
206 | + |
|
207 | + |
|
208 | + /** |
|
209 | + * admin_init |
|
210 | + */ |
|
211 | + public function admin_init() |
|
212 | + { |
|
213 | + EE_Registry::$i18n_js_strings = array_merge( |
|
214 | + EE_Registry::$i18n_js_strings, |
|
215 | + array( |
|
216 | + 'image_confirm' => esc_html__( |
|
217 | + 'Do you really want to delete this image? Please remember to update your event to complete the removal.', |
|
218 | + 'event_espresso' |
|
219 | + ), |
|
220 | + 'event_starts_on' => esc_html__('Event Starts on', 'event_espresso'), |
|
221 | + 'event_ends_on' => esc_html__('Event Ends on', 'event_espresso'), |
|
222 | + 'event_datetime_actions' => esc_html__('Actions', 'event_espresso'), |
|
223 | + 'event_clone_dt_msg' => esc_html__('Clone this Event Date and Time', 'event_espresso'), |
|
224 | + 'remove_event_dt_msg' => esc_html__('Remove this Event Time', 'event_espresso'), |
|
225 | + ) |
|
226 | + ); |
|
227 | + } |
|
228 | + |
|
229 | + |
|
230 | + /** |
|
231 | + * This will be used to listen for any heartbeat data packages coming via the WordPress heartbeat API and handle |
|
232 | + * accordingly. |
|
233 | + * |
|
234 | + * @param array $response The existing heartbeat response array. |
|
235 | + * @param array $data The incoming data package. |
|
236 | + * @return array possibly appended response. |
|
237 | + */ |
|
238 | + public function heartbeat_response($response, $data) |
|
239 | + { |
|
240 | + /** |
|
241 | + * check whether count of tickets is approaching the potential |
|
242 | + * limits for the server. |
|
243 | + */ |
|
244 | + if (! empty($data['input_count'])) { |
|
245 | + $response['max_input_vars_check'] = EE_Registry::instance()->CFG->environment->max_input_vars_limit_check( |
|
246 | + $data['input_count'] |
|
247 | + ); |
|
248 | + } |
|
249 | + return $response; |
|
250 | + } |
|
251 | + |
|
252 | + |
|
253 | + /** |
|
254 | + * Add per page screen options to the default ticket list table view. |
|
255 | + */ |
|
256 | + protected function _add_screen_options_ticket_list_table() |
|
257 | + { |
|
258 | + $this->_per_page_screen_option(); |
|
259 | + } |
|
260 | + |
|
261 | + |
|
262 | + /** |
|
263 | + * @param string $return |
|
264 | + * @param int $id |
|
265 | + * @param string $new_title |
|
266 | + * @param string $new_slug |
|
267 | + * @return string |
|
268 | + */ |
|
269 | + public function extra_permalink_field_buttons($return, $id, $new_title, $new_slug) |
|
270 | + { |
|
271 | + $return = parent::extra_permalink_field_buttons($return, $id, $new_title, $new_slug); |
|
272 | + //make sure this is only when editing |
|
273 | + if (! empty($id)) { |
|
274 | + $href = EE_Admin_Page::add_query_args_and_nonce( |
|
275 | + array('action' => 'duplicate_event', 'EVT_ID' => $id), |
|
276 | + $this->_admin_base_url |
|
277 | + ); |
|
278 | + $title = esc_attr__('Duplicate Event', 'event_espresso'); |
|
279 | + $return .= '<a href="' |
|
280 | + . $href |
|
281 | + . '" title="' |
|
282 | + . $title |
|
283 | + . '" id="ee-duplicate-event-button" class="button button-small" value="duplicate_event">' |
|
284 | + . $title |
|
285 | + . '</button>'; |
|
286 | + } |
|
287 | + return $return; |
|
288 | + } |
|
289 | + |
|
290 | + |
|
291 | + /** |
|
292 | + * Set the list table views for the default ticket list table view. |
|
293 | + */ |
|
294 | + public function _set_list_table_views_ticket_list_table() |
|
295 | + { |
|
296 | + $this->_views = array( |
|
297 | + 'all' => array( |
|
298 | + 'slug' => 'all', |
|
299 | + 'label' => esc_html__('All', 'event_espresso'), |
|
300 | + 'count' => 0, |
|
301 | + 'bulk_action' => array( |
|
302 | + 'trash_tickets' => esc_html__('Move to Trash', 'event_espresso'), |
|
303 | + ), |
|
304 | + ), |
|
305 | + 'trashed' => array( |
|
306 | + 'slug' => 'trashed', |
|
307 | + 'label' => esc_html__('Trash', 'event_espresso'), |
|
308 | + 'count' => 0, |
|
309 | + 'bulk_action' => array( |
|
310 | + 'restore_tickets' => esc_html__('Restore from Trash', 'event_espresso'), |
|
311 | + 'delete_tickets' => esc_html__('Delete Permanently', 'event_espresso'), |
|
312 | + ), |
|
313 | + ), |
|
314 | + ); |
|
315 | + } |
|
316 | + |
|
317 | + |
|
318 | + /** |
|
319 | + * Enqueue scripts and styles for the event editor. |
|
320 | + */ |
|
321 | + public function load_scripts_styles_edit() |
|
322 | + { |
|
323 | + wp_register_script( |
|
324 | + 'ee-event-editor-heartbeat', |
|
325 | + EVENTS_CAF_ASSETS_URL . 'event-editor-heartbeat.js', |
|
326 | + array('ee_admin_js', 'heartbeat'), |
|
327 | + EVENT_ESPRESSO_VERSION, |
|
328 | + true |
|
329 | + ); |
|
330 | + wp_enqueue_script('ee-accounting'); |
|
331 | + //styles |
|
332 | + wp_enqueue_style('espresso-ui-theme'); |
|
333 | + wp_enqueue_script('event_editor_js'); |
|
334 | + wp_enqueue_script('ee-event-editor-heartbeat'); |
|
335 | + } |
|
336 | + |
|
337 | + |
|
338 | + /** |
|
339 | + * Returns template for the additional datetime. |
|
340 | + * @param $template |
|
341 | + * @param $template_args |
|
342 | + * @return mixed |
|
343 | + * @throws DomainException |
|
344 | + */ |
|
345 | + public function add_additional_datetime_button($template, $template_args) |
|
346 | + { |
|
347 | + return EEH_Template::display_template( |
|
348 | + EVENTS_CAF_TEMPLATE_PATH . 'event_datetime_add_additional_time.template.php', |
|
349 | + $template_args, |
|
350 | + true |
|
351 | + ); |
|
352 | + } |
|
353 | + |
|
354 | + |
|
355 | + /** |
|
356 | + * Returns the template for cloning a datetime. |
|
357 | + * @param $template |
|
358 | + * @param $template_args |
|
359 | + * @return mixed |
|
360 | + * @throws DomainException |
|
361 | + */ |
|
362 | + public function add_datetime_clone_button($template, $template_args) |
|
363 | + { |
|
364 | + return EEH_Template::display_template( |
|
365 | + EVENTS_CAF_TEMPLATE_PATH . 'event_datetime_metabox_clone_button.template.php', |
|
366 | + $template_args, |
|
367 | + true |
|
368 | + ); |
|
369 | + } |
|
370 | + |
|
371 | + |
|
372 | + /** |
|
373 | + * Returns the template for datetime timezones. |
|
374 | + * @param $template |
|
375 | + * @param $template_args |
|
376 | + * @return mixed |
|
377 | + * @throws DomainException |
|
378 | + */ |
|
379 | + public function datetime_timezones_template($template, $template_args) |
|
380 | + { |
|
381 | + return EEH_Template::display_template( |
|
382 | + EVENTS_CAF_TEMPLATE_PATH . 'event_datetime_timezones.template.php', |
|
383 | + $template_args, |
|
384 | + true |
|
385 | + ); |
|
386 | + } |
|
387 | + |
|
388 | + |
|
389 | + /** |
|
390 | + * Sets the views for the default list table view. |
|
391 | + */ |
|
392 | + protected function _set_list_table_views_default() |
|
393 | + { |
|
394 | + parent::_set_list_table_views_default(); |
|
395 | + $new_views = array( |
|
396 | + 'today' => array( |
|
397 | + 'slug' => 'today', |
|
398 | + 'label' => esc_html__('Today', 'event_espresso'), |
|
399 | + 'count' => $this->total_events_today(), |
|
400 | + 'bulk_action' => array( |
|
401 | + 'trash_events' => esc_html__('Move to Trash', 'event_espresso'), |
|
402 | + ), |
|
403 | + ), |
|
404 | + 'month' => array( |
|
405 | + 'slug' => 'month', |
|
406 | + 'label' => esc_html__('This Month', 'event_espresso'), |
|
407 | + 'count' => $this->total_events_this_month(), |
|
408 | + 'bulk_action' => array( |
|
409 | + 'trash_events' => esc_html__('Move to Trash', 'event_espresso'), |
|
410 | + ), |
|
411 | + ), |
|
412 | + ); |
|
413 | + $this->_views = array_merge($this->_views, $new_views); |
|
414 | + } |
|
415 | + |
|
416 | + |
|
417 | + /** |
|
418 | + * Returns the extra action links for the default list table view. |
|
419 | + * @param array $action_links |
|
420 | + * @param \EE_Event $event |
|
421 | + * @return array |
|
422 | + * @throws EE_Error |
|
423 | + */ |
|
424 | + public function extra_list_table_actions(array $action_links, \EE_Event $event) |
|
425 | + { |
|
426 | + if (EE_Registry::instance()->CAP->current_user_can( |
|
427 | + 'ee_read_registrations', |
|
428 | + 'espresso_registrations_reports', |
|
429 | + $event->ID() |
|
430 | + ) |
|
431 | + ) { |
|
432 | + $reports_query_args = array( |
|
433 | + 'action' => 'reports', |
|
434 | + 'EVT_ID' => $event->ID(), |
|
435 | + ); |
|
436 | + $reports_link = EE_Admin_Page::add_query_args_and_nonce($reports_query_args, REG_ADMIN_URL); |
|
437 | + $action_links[] = '<a href="' |
|
438 | + . $reports_link |
|
439 | + . '" title="' |
|
440 | + . esc_attr__('View Report', 'event_espresso') |
|
441 | + . '"><div class="dashicons dashicons-chart-bar"></div></a>' |
|
442 | + . "\n\t"; |
|
443 | + } |
|
444 | + if (EE_Registry::instance()->CAP->current_user_can('ee_read_global_messages', 'view_filtered_messages')) { |
|
445 | + EE_Registry::instance()->load_helper('MSG_Template'); |
|
446 | + $action_links[] = EEH_MSG_Template::get_message_action_link( |
|
447 | + 'see_notifications_for', |
|
448 | + null, |
|
449 | + array('EVT_ID' => $event->ID()) |
|
450 | + ); |
|
451 | + } |
|
452 | + return $action_links; |
|
453 | + } |
|
454 | + |
|
455 | + |
|
456 | + /** |
|
457 | + * @param $items |
|
458 | + * @return mixed |
|
459 | + */ |
|
460 | + public function additional_legend_items($items) |
|
461 | + { |
|
462 | + if (EE_Registry::instance()->CAP->current_user_can( |
|
463 | + 'ee_read_registrations', |
|
464 | + 'espresso_registrations_reports' |
|
465 | + ) |
|
466 | + ) { |
|
467 | + $items['reports'] = array( |
|
468 | + 'class' => 'dashicons dashicons-chart-bar', |
|
469 | + 'desc' => esc_html__('Event Reports', 'event_espresso'), |
|
470 | + ); |
|
471 | + } |
|
472 | + if (EE_Registry::instance()->CAP->current_user_can('ee_read_global_messages', 'view_filtered_messages')) { |
|
473 | + $related_for_icon = EEH_MSG_Template::get_message_action_icon('see_notifications_for'); |
|
474 | + if (isset($related_for_icon['css_class']) && isset($related_for_icon['label'])) { |
|
475 | + $items['view_related_messages'] = array( |
|
476 | + 'class' => $related_for_icon['css_class'], |
|
477 | + 'desc' => $related_for_icon['label'], |
|
478 | + ); |
|
479 | + } |
|
480 | + } |
|
481 | + return $items; |
|
482 | + } |
|
483 | + |
|
484 | + |
|
485 | + /** |
|
486 | + * This is the callback method for the duplicate event route |
|
487 | + * Method looks for 'EVT_ID' in the request and retrieves that event and its details and duplicates them |
|
488 | + * into a new event. We add a hook so that any plugins that add extra event details can hook into this |
|
489 | + * action. Note that the dupe will have **DUPLICATE** as its title and slug. |
|
490 | + * After duplication the redirect is to the new event edit page. |
|
491 | + * |
|
492 | + * @return void |
|
493 | + * @access protected |
|
494 | + * @throws EE_Error If EE_Event is not available with given ID |
|
495 | + */ |
|
496 | + protected function _duplicate_event() |
|
497 | + { |
|
498 | + // first make sure the ID for the event is in the request. |
|
499 | + // If it isn't then we need to bail and redirect back to overview list table (cause how did we get here?) |
|
500 | + if (! isset($this->_req_data['EVT_ID'])) { |
|
501 | + EE_Error::add_error( |
|
502 | + esc_html__( |
|
503 | + 'In order to duplicate an event an Event ID is required. None was given.', |
|
504 | + 'event_espresso' |
|
505 | + ), |
|
506 | + __FILE__, |
|
507 | + __FUNCTION__, |
|
508 | + __LINE__ |
|
509 | + ); |
|
510 | + $this->_redirect_after_action(false, '', '', array(), true); |
|
511 | + return; |
|
512 | + } |
|
513 | + //k we've got EVT_ID so let's use that to get the event we'll duplicate |
|
514 | + $orig_event = EEM_Event::instance()->get_one_by_ID($this->_req_data['EVT_ID']); |
|
515 | + if (! $orig_event instanceof EE_Event) { |
|
516 | + throw new EE_Error( |
|
517 | + sprintf( |
|
518 | + esc_html__('An EE_Event object could not be retrieved for the given ID (%s)', 'event_espresso'), |
|
519 | + $this->_req_data['EVT_ID'] |
|
520 | + ) |
|
521 | + ); |
|
522 | + } |
|
523 | + //k now let's clone the $orig_event before getting relations |
|
524 | + $new_event = clone $orig_event; |
|
525 | + //original datetimes |
|
526 | + $orig_datetimes = $orig_event->get_many_related('Datetime'); |
|
527 | + //other original relations |
|
528 | + $orig_ven = $orig_event->get_many_related('Venue'); |
|
529 | + //reset the ID and modify other details to make it clear this is a dupe |
|
530 | + $new_event->set('EVT_ID', 0); |
|
531 | + $new_name = $new_event->name() . ' ' . esc_html__('**DUPLICATE**', 'event_espresso'); |
|
532 | + $new_event->set('EVT_name', $new_name); |
|
533 | + $new_event->set( |
|
534 | + 'EVT_slug', |
|
535 | + wp_unique_post_slug( |
|
536 | + sanitize_title($orig_event->name()), |
|
537 | + 0, |
|
538 | + 'publish', |
|
539 | + 'espresso_events', |
|
540 | + 0 |
|
541 | + ) |
|
542 | + ); |
|
543 | + $new_event->set('status', 'draft'); |
|
544 | + //duplicate discussion settings |
|
545 | + $new_event->set('comment_status', $orig_event->get('comment_status')); |
|
546 | + $new_event->set('ping_status', $orig_event->get('ping_status')); |
|
547 | + //save the new event |
|
548 | + $new_event->save(); |
|
549 | + //venues |
|
550 | + foreach ($orig_ven as $ven) { |
|
551 | + $new_event->_add_relation_to($ven, 'Venue'); |
|
552 | + } |
|
553 | + $new_event->save(); |
|
554 | + //now we need to get the question group relations and handle that |
|
555 | + //first primary question groups |
|
556 | + $orig_primary_qgs = $orig_event->get_many_related( |
|
557 | + 'Question_Group', |
|
558 | + array(array('Event_Question_Group.EQG_primary' => 1)) |
|
559 | + ); |
|
560 | + if (! empty($orig_primary_qgs)) { |
|
561 | + foreach ($orig_primary_qgs as $id => $obj) { |
|
562 | + if ($obj instanceof EE_Question_Group) { |
|
563 | + $new_event->_add_relation_to($obj, 'Question_Group', array('EQG_primary' => 1)); |
|
564 | + } |
|
565 | + } |
|
566 | + } |
|
567 | + //next additional attendee question groups |
|
568 | + $orig_additional_qgs = $orig_event->get_many_related( |
|
569 | + 'Question_Group', |
|
570 | + array(array('Event_Question_Group.EQG_primary' => 0)) |
|
571 | + ); |
|
572 | + if (! empty($orig_additional_qgs)) { |
|
573 | + foreach ($orig_additional_qgs as $id => $obj) { |
|
574 | + if ($obj instanceof EE_Question_Group) { |
|
575 | + $new_event->_add_relation_to($obj, 'Question_Group', array('EQG_primary' => 0)); |
|
576 | + } |
|
577 | + } |
|
578 | + } |
|
579 | + |
|
580 | + $new_event->save(); |
|
581 | + |
|
582 | + //k now that we have the new event saved we can loop through the datetimes and start adding relations. |
|
583 | + $cloned_tickets = array(); |
|
584 | + foreach ($orig_datetimes as $orig_dtt) { |
|
585 | + if (! $orig_dtt instanceof EE_Datetime) { |
|
586 | + continue; |
|
587 | + } |
|
588 | + $new_dtt = clone $orig_dtt; |
|
589 | + $orig_tkts = $orig_dtt->tickets(); |
|
590 | + //save new dtt then add to event |
|
591 | + $new_dtt->set('DTT_ID', 0); |
|
592 | + $new_dtt->set('DTT_sold', 0); |
|
593 | + $new_dtt->set_reserved(0); |
|
594 | + $new_dtt->save(); |
|
595 | + $new_event->_add_relation_to($new_dtt, 'Datetime'); |
|
596 | + $new_event->save(); |
|
597 | + //now let's get the ticket relations setup. |
|
598 | + foreach ((array)$orig_tkts as $orig_tkt) { |
|
599 | + //it's possible a datetime will have no tickets so let's verify we HAVE a ticket first. |
|
600 | + if (! $orig_tkt instanceof EE_Ticket) { |
|
601 | + continue; |
|
602 | + } |
|
603 | + //is this ticket archived? If it is then let's skip |
|
604 | + if ($orig_tkt->get('TKT_deleted')) { |
|
605 | + continue; |
|
606 | + } |
|
607 | + // does this original ticket already exist in the clone_tickets cache? |
|
608 | + // If so we'll just use the new ticket from it. |
|
609 | + if (isset($cloned_tickets[$orig_tkt->ID()])) { |
|
610 | + $new_tkt = $cloned_tickets[$orig_tkt->ID()]; |
|
611 | + } else { |
|
612 | + $new_tkt = clone $orig_tkt; |
|
613 | + //get relations on the $orig_tkt that we need to setup. |
|
614 | + $orig_prices = $orig_tkt->prices(); |
|
615 | + $new_tkt->set('TKT_ID', 0); |
|
616 | + $new_tkt->set('TKT_sold', 0); |
|
617 | + $new_tkt->set('TKT_reserved', 0); |
|
618 | + $new_tkt->save(); //make sure new ticket has ID. |
|
619 | + //price relations on new ticket need to be setup. |
|
620 | + foreach ($orig_prices as $orig_price) { |
|
621 | + $new_price = clone $orig_price; |
|
622 | + $new_price->set('PRC_ID', 0); |
|
623 | + $new_price->save(); |
|
624 | + $new_tkt->_add_relation_to($new_price, 'Price'); |
|
625 | + $new_tkt->save(); |
|
626 | + } |
|
627 | + |
|
628 | + do_action( |
|
629 | + 'AHEE__Extend_Events_Admin_Page___duplicate_event__duplicate_ticket__after', |
|
630 | + $orig_tkt, |
|
631 | + $new_tkt, |
|
632 | + $orig_prices, |
|
633 | + $orig_event, |
|
634 | + $orig_dtt, |
|
635 | + $new_dtt |
|
636 | + ); |
|
637 | + } |
|
638 | + // k now we can add the new ticket as a relation to the new datetime |
|
639 | + // and make sure its added to our cached $cloned_tickets array |
|
640 | + // for use with later datetimes that have the same ticket. |
|
641 | + $new_dtt->_add_relation_to($new_tkt, 'Ticket'); |
|
642 | + $new_dtt->save(); |
|
643 | + $cloned_tickets[$orig_tkt->ID()] = $new_tkt; |
|
644 | + } |
|
645 | + } |
|
646 | + //clone taxonomy information |
|
647 | + $taxonomies_to_clone_with = apply_filters( |
|
648 | + 'FHEE__Extend_Events_Admin_Page___duplicate_event__taxonomies_to_clone', |
|
649 | + array('espresso_event_categories', 'espresso_event_type', 'post_tag') |
|
650 | + ); |
|
651 | + //get terms for original event (notice) |
|
652 | + $orig_terms = wp_get_object_terms($orig_event->ID(), $taxonomies_to_clone_with); |
|
653 | + //loop through terms and add them to new event. |
|
654 | + foreach ($orig_terms as $term) { |
|
655 | + wp_set_object_terms($new_event->ID(), $term->term_id, $term->taxonomy, true); |
|
656 | + } |
|
657 | + |
|
658 | + //duplicate other core WP_Post items for this event. |
|
659 | + //post thumbnail (feature image). |
|
660 | + $feature_image_id = get_post_thumbnail_id($orig_event->ID()); |
|
661 | + if ($feature_image_id) { |
|
662 | + update_post_meta($new_event->ID(), '_thumbnail_id', $feature_image_id); |
|
663 | + } |
|
664 | + |
|
665 | + //duplicate page_template setting |
|
666 | + $page_template = get_post_meta($orig_event->ID(), '_wp_page_template', true); |
|
667 | + if ($page_template) { |
|
668 | + update_post_meta($new_event->ID(), '_wp_page_template', $page_template); |
|
669 | + } |
|
670 | + |
|
671 | + do_action('AHEE__Extend_Events_Admin_Page___duplicate_event__after', $new_event, $orig_event); |
|
672 | + //now let's redirect to the edit page for this duplicated event if we have a new event id. |
|
673 | + if ($new_event->ID()) { |
|
674 | + $redirect_args = array( |
|
675 | + 'post' => $new_event->ID(), |
|
676 | + 'action' => 'edit', |
|
677 | + ); |
|
678 | + EE_Error::add_success( |
|
679 | + esc_html__( |
|
680 | + 'Event successfully duplicated. Please review the details below and make any necessary edits', |
|
681 | + 'event_espresso' |
|
682 | + ) |
|
683 | + ); |
|
684 | + } else { |
|
685 | + $redirect_args = array( |
|
686 | + 'action' => 'default', |
|
687 | + ); |
|
688 | + EE_Error::add_error( |
|
689 | + esc_html__('Not able to duplicate event. Something went wrong.', 'event_espresso'), |
|
690 | + __FILE__, |
|
691 | + __FUNCTION__, |
|
692 | + __LINE__ |
|
693 | + ); |
|
694 | + } |
|
695 | + $this->_redirect_after_action(false, '', '', $redirect_args, true); |
|
696 | + } |
|
697 | + |
|
698 | + |
|
699 | + /** |
|
700 | + * Generates output for the import page. |
|
701 | + * @throws DomainException |
|
702 | + */ |
|
703 | + protected function _import_page() |
|
704 | + { |
|
705 | + $title = esc_html__('Import', 'event_espresso'); |
|
706 | + $intro = esc_html__( |
|
707 | + 'If you have a previously exported Event Espresso 4 information in a Comma Separated Value (CSV) file format, you can upload the file here: ', |
|
708 | + 'event_espresso' |
|
709 | + ); |
|
710 | + $form_url = EVENTS_ADMIN_URL; |
|
711 | + $action = 'import_events'; |
|
712 | + $type = 'csv'; |
|
713 | + $this->_template_args['form'] = EE_Import::instance()->upload_form( |
|
714 | + $title, $intro, $form_url, $action, $type |
|
715 | + ); |
|
716 | + $this->_template_args['sample_file_link'] = EE_Admin_Page::add_query_args_and_nonce( |
|
717 | + array('action' => 'sample_export_file'), |
|
718 | + $this->_admin_base_url |
|
719 | + ); |
|
720 | + $content = EEH_Template::display_template( |
|
721 | + EVENTS_CAF_TEMPLATE_PATH . 'import_page.template.php', |
|
722 | + $this->_template_args, |
|
723 | + true |
|
724 | + ); |
|
725 | + $this->_template_args['admin_page_content'] = $content; |
|
726 | + $this->display_admin_page_with_sidebar(); |
|
727 | + } |
|
728 | + |
|
729 | + |
|
730 | + /** |
|
731 | + * _import_events |
|
732 | + * This handles displaying the screen and running imports for importing events. |
|
733 | + * |
|
734 | + * @return void |
|
735 | + */ |
|
736 | + protected function _import_events() |
|
737 | + { |
|
738 | + require_once(EE_CLASSES . 'EE_Import.class.php'); |
|
739 | + $success = EE_Import::instance()->import(); |
|
740 | + $this->_redirect_after_action($success, 'Import File', 'ran', array('action' => 'import_page'), true); |
|
741 | + } |
|
742 | + |
|
743 | + |
|
744 | + /** |
|
745 | + * _events_export |
|
746 | + * Will export all (or just the given event) to a Excel compatible file. |
|
747 | + * |
|
748 | + * @access protected |
|
749 | + * @return void |
|
750 | + */ |
|
751 | + protected function _events_export() |
|
752 | + { |
|
753 | + if (isset($this->_req_data['EVT_ID'])) { |
|
754 | + $event_ids = $this->_req_data['EVT_ID']; |
|
755 | + } elseif (isset($this->_req_data['EVT_IDs'])) { |
|
756 | + $event_ids = $this->_req_data['EVT_IDs']; |
|
757 | + } else { |
|
758 | + $event_ids = null; |
|
759 | + } |
|
760 | + //todo: I don't like doing this but it'll do until we modify EE_Export Class. |
|
761 | + $new_request_args = array( |
|
762 | + 'export' => 'report', |
|
763 | + 'action' => 'all_event_data', |
|
764 | + 'EVT_ID' => $event_ids, |
|
765 | + ); |
|
766 | + $this->_req_data = array_merge($this->_req_data, $new_request_args); |
|
767 | + if (is_readable(EE_CLASSES . 'EE_Export.class.php')) { |
|
768 | + require_once(EE_CLASSES . 'EE_Export.class.php'); |
|
769 | + $EE_Export = EE_Export::instance($this->_req_data); |
|
770 | + $EE_Export->export(); |
|
771 | + } |
|
772 | + } |
|
773 | + |
|
774 | + |
|
775 | + /** |
|
776 | + * handle category exports() |
|
777 | + * |
|
778 | + * @return void |
|
779 | + */ |
|
780 | + protected function _categories_export() |
|
781 | + { |
|
782 | + //todo: I don't like doing this but it'll do until we modify EE_Export Class. |
|
783 | + $new_request_args = array( |
|
784 | + 'export' => 'report', |
|
785 | + 'action' => 'categories', |
|
786 | + 'category_ids' => $this->_req_data['EVT_CAT_ID'], |
|
787 | + ); |
|
788 | + $this->_req_data = array_merge($this->_req_data, $new_request_args); |
|
789 | + if (is_readable(EE_CLASSES . 'EE_Export.class.php')) { |
|
790 | + require_once(EE_CLASSES . 'EE_Export.class.php'); |
|
791 | + $EE_Export = EE_Export::instance($this->_req_data); |
|
792 | + $EE_Export->export(); |
|
793 | + } |
|
794 | + } |
|
795 | + |
|
796 | + |
|
797 | + /** |
|
798 | + * Creates a sample CSV file for importing |
|
799 | + */ |
|
800 | + protected function _sample_export_file() |
|
801 | + { |
|
802 | + // require_once(EE_CLASSES . 'EE_Export.class.php'); |
|
803 | + EE_Export::instance()->export_sample(); |
|
804 | + } |
|
805 | + |
|
806 | + |
|
807 | + /************* Template Settings *************/ |
|
808 | + /** |
|
809 | + * Generates template settings page output |
|
810 | + * @throws DomainException |
|
811 | + * @throws EE_Error |
|
812 | + */ |
|
813 | + protected function _template_settings() |
|
814 | + { |
|
815 | + $this->_template_args['values'] = $this->_yes_no_values; |
|
816 | + /** |
|
817 | + * Note leaving this filter in for backward compatibility this was moved in 4.6.x |
|
818 | + * from General_Settings_Admin_Page to here. |
|
819 | + */ |
|
820 | + $this->_template_args = apply_filters( |
|
821 | + 'FHEE__General_Settings_Admin_Page__template_settings__template_args', |
|
822 | + $this->_template_args |
|
823 | + ); |
|
824 | + $this->_set_add_edit_form_tags('update_template_settings'); |
|
825 | + $this->_set_publish_post_box_vars(null, false, false, null, false); |
|
826 | + $this->_template_args['admin_page_content'] = EEH_Template::display_template( |
|
827 | + EVENTS_CAF_TEMPLATE_PATH . 'template_settings.template.php', |
|
828 | + $this->_template_args, |
|
829 | + true |
|
830 | + ); |
|
831 | + $this->display_admin_page_with_sidebar(); |
|
832 | + } |
|
833 | + |
|
834 | + |
|
835 | + /** |
|
836 | + * Handler for updating template settings. |
|
837 | + */ |
|
838 | + protected function _update_template_settings() |
|
839 | + { |
|
840 | + /** |
|
841 | + * Note leaving this filter in for backward compatibility this was moved in 4.6.x |
|
842 | + * from General_Settings_Admin_Page to here. |
|
843 | + */ |
|
844 | + EE_Registry::instance()->CFG->template_settings = apply_filters( |
|
845 | + 'FHEE__General_Settings_Admin_Page__update_template_settings__data', |
|
846 | + EE_Registry::instance()->CFG->template_settings, |
|
847 | + $this->_req_data |
|
848 | + ); |
|
849 | + //update custom post type slugs and detect if we need to flush rewrite rules |
|
850 | + $old_slug = EE_Registry::instance()->CFG->core->event_cpt_slug; |
|
851 | + EE_Registry::instance()->CFG->core->event_cpt_slug = empty($this->_req_data['event_cpt_slug']) |
|
852 | + ? EE_Registry::instance()->CFG->core->event_cpt_slug |
|
853 | + : sanitize_title_with_dashes($this->_req_data['event_cpt_slug']); |
|
854 | + $what = 'Template Settings'; |
|
855 | + $success = $this->_update_espresso_configuration( |
|
856 | + $what, |
|
857 | + EE_Registry::instance()->CFG->template_settings, |
|
858 | + __FILE__, |
|
859 | + __FUNCTION__, |
|
860 | + __LINE__ |
|
861 | + ); |
|
862 | + if (EE_Registry::instance()->CFG->core->event_cpt_slug != $old_slug) { |
|
863 | + update_option('ee_flush_rewrite_rules', true); |
|
864 | + } |
|
865 | + $this->_redirect_after_action($success, $what, 'updated', array('action' => 'template_settings')); |
|
866 | + } |
|
867 | + |
|
868 | + |
|
869 | + /** |
|
870 | + * _premium_event_editor_meta_boxes |
|
871 | + * add all metaboxes related to the event_editor |
|
872 | + * |
|
873 | + * @access protected |
|
874 | + * @return void |
|
875 | + * @throws EE_Error |
|
876 | + */ |
|
877 | + protected function _premium_event_editor_meta_boxes() |
|
878 | + { |
|
879 | + $this->verify_cpt_object(); |
|
880 | + add_meta_box( |
|
881 | + 'espresso_event_editor_event_options', |
|
882 | + esc_html__('Event Registration Options', 'event_espresso'), |
|
883 | + array($this, 'registration_options_meta_box'), |
|
884 | + $this->page_slug, |
|
885 | + 'side', |
|
886 | + 'core' |
|
887 | + ); |
|
888 | + } |
|
889 | + |
|
890 | + |
|
891 | + /** |
|
892 | + * override caf metabox |
|
893 | + * |
|
894 | + * @return void |
|
895 | + * @throws DomainException |
|
896 | + */ |
|
897 | + public function registration_options_meta_box() |
|
898 | + { |
|
899 | + $yes_no_values = array( |
|
900 | + array('id' => true, 'text' => esc_html__('Yes', 'event_espresso')), |
|
901 | + array('id' => false, 'text' => esc_html__('No', 'event_espresso')), |
|
902 | + ); |
|
903 | + $default_reg_status_values = EEM_Registration::reg_status_array( |
|
904 | + array( |
|
905 | + EEM_Registration::status_id_cancelled, |
|
906 | + EEM_Registration::status_id_declined, |
|
907 | + EEM_Registration::status_id_incomplete, |
|
908 | + EEM_Registration::status_id_wait_list, |
|
909 | + ), |
|
910 | + true |
|
911 | + ); |
|
912 | + $template_args['active_status'] = $this->_cpt_model_obj->pretty_active_status(false); |
|
913 | + $template_args['_event'] = $this->_cpt_model_obj; |
|
914 | + $template_args['additional_limit'] = $this->_cpt_model_obj->additional_limit(); |
|
915 | + $template_args['default_registration_status'] = EEH_Form_Fields::select_input( |
|
916 | + 'default_reg_status', |
|
917 | + $default_reg_status_values, |
|
918 | + $this->_cpt_model_obj->default_registration_status() |
|
919 | + ); |
|
920 | + $template_args['display_description'] = EEH_Form_Fields::select_input( |
|
921 | + 'display_desc', |
|
922 | + $yes_no_values, |
|
923 | + $this->_cpt_model_obj->display_description() |
|
924 | + ); |
|
925 | + $template_args['display_ticket_selector'] = EEH_Form_Fields::select_input( |
|
926 | + 'display_ticket_selector', |
|
927 | + $yes_no_values, |
|
928 | + $this->_cpt_model_obj->display_ticket_selector(), |
|
929 | + '', |
|
930 | + '', |
|
931 | + false |
|
932 | + ); |
|
933 | + $template_args['EVT_default_registration_status'] = EEH_Form_Fields::select_input( |
|
934 | + 'EVT_default_registration_status', |
|
935 | + $default_reg_status_values, |
|
936 | + $this->_cpt_model_obj->default_registration_status() |
|
937 | + ); |
|
938 | + $template_args['additional_registration_options'] = apply_filters( |
|
939 | + 'FHEE__Events_Admin_Page__registration_options_meta_box__additional_registration_options', |
|
940 | + '', |
|
941 | + $template_args, |
|
942 | + $yes_no_values, |
|
943 | + $default_reg_status_values |
|
944 | + ); |
|
945 | + EEH_Template::display_template( |
|
946 | + EVENTS_CAF_TEMPLATE_PATH . 'event_registration_options.template.php', |
|
947 | + $template_args |
|
948 | + ); |
|
949 | + } |
|
950 | + |
|
951 | + |
|
952 | + |
|
953 | + /** |
|
954 | + * wp_list_table_mods for caf |
|
955 | + * ============================ |
|
956 | + */ |
|
957 | + /** |
|
958 | + * hook into list table filters and provide filters for caffeinated list table |
|
959 | + * |
|
960 | + * @param array $old_filters any existing filters present |
|
961 | + * @param array $list_table_obj the list table object |
|
962 | + * @return array new filters |
|
963 | + */ |
|
964 | + public function list_table_filters($old_filters, $list_table_obj) |
|
965 | + { |
|
966 | + $filters = array(); |
|
967 | + //first month/year filters |
|
968 | + $filters[] = $this->espresso_event_months_dropdown(); |
|
969 | + $status = isset($this->_req_data['status']) ? $this->_req_data['status'] : null; |
|
970 | + //active status dropdown |
|
971 | + if ($status !== 'draft') { |
|
972 | + $filters[] = $this->active_status_dropdown( |
|
973 | + isset($this->_req_data['active_status']) ? $this->_req_data['active_status'] : '' |
|
974 | + ); |
|
975 | + } |
|
976 | + //category filter |
|
977 | + $filters[] = $this->category_dropdown(); |
|
978 | + return array_merge($old_filters, $filters); |
|
979 | + } |
|
980 | + |
|
981 | + |
|
982 | + /** |
|
983 | + * espresso_event_months_dropdown |
|
984 | + * |
|
985 | + * @access public |
|
986 | + * @return string dropdown listing month/year selections for events. |
|
987 | + */ |
|
988 | + public function espresso_event_months_dropdown() |
|
989 | + { |
|
990 | + // what we need to do is get all PRIMARY datetimes for all events to filter on. |
|
991 | + // Note we need to include any other filters that are set! |
|
992 | + $status = isset($this->_req_data['status']) ? $this->_req_data['status'] : null; |
|
993 | + //categories? |
|
994 | + $category = isset($this->_req_data['EVT_CAT']) && $this->_req_data['EVT_CAT'] > 0 |
|
995 | + ? $this->_req_data['EVT_CAT'] |
|
996 | + : null; |
|
997 | + //active status? |
|
998 | + $active_status = isset($this->_req_data['active_status']) ? $this->_req_data['active_status'] : null; |
|
999 | + $cur_date = isset($this->_req_data['month_range']) ? $this->_req_data['month_range'] : ''; |
|
1000 | + return EEH_Form_Fields::generate_event_months_dropdown($cur_date, $status, $category, $active_status); |
|
1001 | + } |
|
1002 | + |
|
1003 | + |
|
1004 | + /** |
|
1005 | + * returns a list of "active" statuses on the event |
|
1006 | + * |
|
1007 | + * @param string $current_value whatever the current active status is |
|
1008 | + * @return string |
|
1009 | + */ |
|
1010 | + public function active_status_dropdown($current_value = '') |
|
1011 | + { |
|
1012 | + $select_name = 'active_status'; |
|
1013 | + $values = array( |
|
1014 | + 'none' => esc_html__('Show Active/Inactive', 'event_espresso'), |
|
1015 | + 'active' => esc_html__('Active', 'event_espresso'), |
|
1016 | + 'upcoming' => esc_html__('Upcoming', 'event_espresso'), |
|
1017 | + 'expired' => esc_html__('Expired', 'event_espresso'), |
|
1018 | + 'inactive' => esc_html__('Inactive', 'event_espresso'), |
|
1019 | + ); |
|
1020 | + $id = 'id="espresso-active-status-dropdown-filter"'; |
|
1021 | + $class = 'wide'; |
|
1022 | + return EEH_Form_Fields::select_input($select_name, $values, $current_value, $id, $class); |
|
1023 | + } |
|
1024 | + |
|
1025 | + |
|
1026 | + /** |
|
1027 | + * output a dropdown of the categories for the category filter on the event admin list table |
|
1028 | + * |
|
1029 | + * @access public |
|
1030 | + * @return string html |
|
1031 | + */ |
|
1032 | + public function category_dropdown() |
|
1033 | + { |
|
1034 | + $cur_cat = isset($this->_req_data['EVT_CAT']) ? $this->_req_data['EVT_CAT'] : -1; |
|
1035 | + return EEH_Form_Fields::generate_event_category_dropdown($cur_cat); |
|
1036 | + } |
|
1037 | + |
|
1038 | + |
|
1039 | + /** |
|
1040 | + * get total number of events today |
|
1041 | + * |
|
1042 | + * @access public |
|
1043 | + * @return int |
|
1044 | + * @throws EE_Error |
|
1045 | + */ |
|
1046 | + public function total_events_today() |
|
1047 | + { |
|
1048 | + $start = EEM_Datetime::instance()->convert_datetime_for_query( |
|
1049 | + 'DTT_EVT_start', |
|
1050 | + date('Y-m-d') . ' 00:00:00', |
|
1051 | + 'Y-m-d H:i:s', |
|
1052 | + 'UTC' |
|
1053 | + ); |
|
1054 | + $end = EEM_Datetime::instance()->convert_datetime_for_query( |
|
1055 | + 'DTT_EVT_start', |
|
1056 | + date('Y-m-d') . ' 23:59:59', |
|
1057 | + 'Y-m-d H:i:s', |
|
1058 | + 'UTC' |
|
1059 | + ); |
|
1060 | + $where = array( |
|
1061 | + 'Datetime.DTT_EVT_start' => array('BETWEEN', array($start, $end)), |
|
1062 | + ); |
|
1063 | + $count = EEM_Event::instance()->count(array($where, 'caps' => 'read_admin'), 'EVT_ID', true); |
|
1064 | + return $count; |
|
1065 | + } |
|
1066 | + |
|
1067 | + |
|
1068 | + /** |
|
1069 | + * get total number of events this month |
|
1070 | + * |
|
1071 | + * @access public |
|
1072 | + * @return int |
|
1073 | + * @throws EE_Error |
|
1074 | + */ |
|
1075 | + public function total_events_this_month() |
|
1076 | + { |
|
1077 | + //Dates |
|
1078 | + $this_year_r = date('Y'); |
|
1079 | + $this_month_r = date('m'); |
|
1080 | + $days_this_month = date('t'); |
|
1081 | + $start = EEM_Datetime::instance()->convert_datetime_for_query( |
|
1082 | + 'DTT_EVT_start', |
|
1083 | + $this_year_r . '-' . $this_month_r . '-01 00:00:00', |
|
1084 | + 'Y-m-d H:i:s', |
|
1085 | + 'UTC' |
|
1086 | + ); |
|
1087 | + $end = EEM_Datetime::instance()->convert_datetime_for_query( |
|
1088 | + 'DTT_EVT_start', |
|
1089 | + $this_year_r . '-' . $this_month_r . '-' . $days_this_month . ' 23:59:59', |
|
1090 | + 'Y-m-d H:i:s', |
|
1091 | + 'UTC' |
|
1092 | + ); |
|
1093 | + $where = array( |
|
1094 | + 'Datetime.DTT_EVT_start' => array('BETWEEN', array($start, $end)), |
|
1095 | + ); |
|
1096 | + $count = EEM_Event::instance()->count(array($where, 'caps' => 'read_admin'), 'EVT_ID', true); |
|
1097 | + return $count; |
|
1098 | + } |
|
1099 | + |
|
1100 | + |
|
1101 | + /** DEFAULT TICKETS STUFF **/ |
|
1102 | + |
|
1103 | + /** |
|
1104 | + * Output default tickets list table view. |
|
1105 | + */ |
|
1106 | + public function _tickets_overview_list_table() |
|
1107 | + { |
|
1108 | + $this->_search_btn_label = esc_html__('Tickets', 'event_espresso'); |
|
1109 | + $this->display_admin_list_table_page_with_no_sidebar(); |
|
1110 | + } |
|
1111 | + |
|
1112 | + |
|
1113 | + /** |
|
1114 | + * @param int $per_page |
|
1115 | + * @param bool $count |
|
1116 | + * @param bool $trashed |
|
1117 | + * @return \EE_Soft_Delete_Base_Class[]|int |
|
1118 | + */ |
|
1119 | + public function get_default_tickets($per_page = 10, $count = false, $trashed = false) |
|
1120 | + { |
|
1121 | + $orderby = empty($this->_req_data['orderby']) ? 'TKT_name' : $this->_req_data['orderby']; |
|
1122 | + $order = empty($this->_req_data['order']) ? 'ASC' : $this->_req_data['order']; |
|
1123 | + switch ($orderby) { |
|
1124 | + case 'TKT_name': |
|
1125 | + $orderby = array('TKT_name' => $order); |
|
1126 | + break; |
|
1127 | + case 'TKT_price': |
|
1128 | + $orderby = array('TKT_price' => $order); |
|
1129 | + break; |
|
1130 | + case 'TKT_uses': |
|
1131 | + $orderby = array('TKT_uses' => $order); |
|
1132 | + break; |
|
1133 | + case 'TKT_min': |
|
1134 | + $orderby = array('TKT_min' => $order); |
|
1135 | + break; |
|
1136 | + case 'TKT_max': |
|
1137 | + $orderby = array('TKT_max' => $order); |
|
1138 | + break; |
|
1139 | + case 'TKT_qty': |
|
1140 | + $orderby = array('TKT_qty' => $order); |
|
1141 | + break; |
|
1142 | + } |
|
1143 | + $current_page = isset($this->_req_data['paged']) && ! empty($this->_req_data['paged']) |
|
1144 | + ? $this->_req_data['paged'] |
|
1145 | + : 1; |
|
1146 | + $per_page = isset($this->_req_data['perpage']) && ! empty($this->_req_data['perpage']) |
|
1147 | + ? $this->_req_data['perpage'] |
|
1148 | + : $per_page; |
|
1149 | + $_where = array( |
|
1150 | + 'TKT_is_default' => 1, |
|
1151 | + 'TKT_deleted' => $trashed, |
|
1152 | + ); |
|
1153 | + $offset = ($current_page - 1) * $per_page; |
|
1154 | + $limit = array($offset, $per_page); |
|
1155 | + if (isset($this->_req_data['s'])) { |
|
1156 | + $sstr = '%' . $this->_req_data['s'] . '%'; |
|
1157 | + $_where['OR'] = array( |
|
1158 | + 'TKT_name' => array('LIKE', $sstr), |
|
1159 | + 'TKT_description' => array('LIKE', $sstr), |
|
1160 | + ); |
|
1161 | + } |
|
1162 | + $query_params = array( |
|
1163 | + $_where, |
|
1164 | + 'order_by' => $orderby, |
|
1165 | + 'limit' => $limit, |
|
1166 | + 'group_by' => 'TKT_ID', |
|
1167 | + ); |
|
1168 | + if ($count) { |
|
1169 | + return EEM_Ticket::instance()->count_deleted_and_undeleted(array($_where)); |
|
1170 | + } else { |
|
1171 | + return EEM_Ticket::instance()->get_all_deleted_and_undeleted($query_params); |
|
1172 | + } |
|
1173 | + } |
|
1174 | + |
|
1175 | + |
|
1176 | + /** |
|
1177 | + * @param bool $trash |
|
1178 | + * @throws EE_Error |
|
1179 | + */ |
|
1180 | + protected function _trash_or_restore_ticket($trash = false) |
|
1181 | + { |
|
1182 | + $success = 1; |
|
1183 | + $TKT = EEM_Ticket::instance(); |
|
1184 | + //checkboxes? |
|
1185 | + if (! empty($this->_req_data['checkbox']) && is_array($this->_req_data['checkbox'])) { |
|
1186 | + //if array has more than one element then success message should be plural |
|
1187 | + $success = count($this->_req_data['checkbox']) > 1 ? 2 : 1; |
|
1188 | + //cycle thru the boxes |
|
1189 | + while (list($TKT_ID, $value) = each($this->_req_data['checkbox'])) { |
|
1190 | + if ($trash) { |
|
1191 | + if (! $TKT->delete_by_ID($TKT_ID)) { |
|
1192 | + $success = 0; |
|
1193 | + } |
|
1194 | + } else { |
|
1195 | + if (! $TKT->restore_by_ID($TKT_ID)) { |
|
1196 | + $success = 0; |
|
1197 | + } |
|
1198 | + } |
|
1199 | + } |
|
1200 | + } else { |
|
1201 | + //grab single id and trash |
|
1202 | + $TKT_ID = absint($this->_req_data['TKT_ID']); |
|
1203 | + if ($trash) { |
|
1204 | + if (! $TKT->delete_by_ID($TKT_ID)) { |
|
1205 | + $success = 0; |
|
1206 | + } |
|
1207 | + } else { |
|
1208 | + if (! $TKT->restore_by_ID($TKT_ID)) { |
|
1209 | + $success = 0; |
|
1210 | + } |
|
1211 | + } |
|
1212 | + } |
|
1213 | + $action_desc = $trash ? 'moved to the trash' : 'restored'; |
|
1214 | + $query_args = array( |
|
1215 | + 'action' => 'ticket_list_table', |
|
1216 | + 'status' => $trash ? '' : 'trashed', |
|
1217 | + ); |
|
1218 | + $this->_redirect_after_action($success, 'Tickets', $action_desc, $query_args); |
|
1219 | + } |
|
1220 | + |
|
1221 | + |
|
1222 | + /** |
|
1223 | + * Handles trashing default ticket. |
|
1224 | + */ |
|
1225 | + protected function _delete_ticket() |
|
1226 | + { |
|
1227 | + $success = 1; |
|
1228 | + //checkboxes? |
|
1229 | + if (! empty($this->_req_data['checkbox']) && is_array($this->_req_data['checkbox'])) { |
|
1230 | + //if array has more than one element then success message should be plural |
|
1231 | + $success = count($this->_req_data['checkbox']) > 1 ? 2 : 1; |
|
1232 | + //cycle thru the boxes |
|
1233 | + while (list($TKT_ID, $value) = each($this->_req_data['checkbox'])) { |
|
1234 | + //delete |
|
1235 | + if (! $this->_delete_the_ticket($TKT_ID)) { |
|
1236 | + $success = 0; |
|
1237 | + } |
|
1238 | + } |
|
1239 | + } else { |
|
1240 | + //grab single id and trash |
|
1241 | + $TKT_ID = absint($this->_req_data['TKT_ID']); |
|
1242 | + if (! $this->_delete_the_ticket($TKT_ID)) { |
|
1243 | + $success = 0; |
|
1244 | + } |
|
1245 | + } |
|
1246 | + $action_desc = 'deleted'; |
|
1247 | + $query_args = array( |
|
1248 | + 'action' => 'ticket_list_table', |
|
1249 | + 'status' => 'trashed', |
|
1250 | + ); |
|
1251 | + //fail safe. If the default ticket count === 1 then we need to redirect to event overview. |
|
1252 | + if (EEM_Ticket::instance()->count_deleted_and_undeleted( |
|
1253 | + array(array('TKT_is_default' => 1)), |
|
1254 | + 'TKT_ID', |
|
1255 | + true |
|
1256 | + ) |
|
1257 | + ) { |
|
1258 | + $query_args = array(); |
|
1259 | + } |
|
1260 | + $this->_redirect_after_action($success, 'Tickets', $action_desc, $query_args); |
|
1261 | + } |
|
1262 | + |
|
1263 | + |
|
1264 | + /** |
|
1265 | + * @param int $TKT_ID |
|
1266 | + * @return bool|int |
|
1267 | + * @throws EE_Error |
|
1268 | + */ |
|
1269 | + protected function _delete_the_ticket($TKT_ID) |
|
1270 | + { |
|
1271 | + $tkt = EEM_Ticket::instance()->get_one_by_ID($TKT_ID); |
|
1272 | + $tkt->_remove_relations('Datetime'); |
|
1273 | + //delete all related prices first |
|
1274 | + $tkt->delete_related_permanently('Price'); |
|
1275 | + return $tkt->delete_permanently(); |
|
1276 | + } |
|
1277 | 1277 | } |
@@ -1,6 +1,6 @@ discard block |
||
1 | 1 | <?php use EventEspresso\core\interfaces\InterminableInterface; |
2 | 2 | |
3 | -if ( ! defined( 'EVENT_ESPRESSO_VERSION')) {exit('No direct script access allowed');} |
|
3 | +if ( ! defined('EVENT_ESPRESSO_VERSION')) {exit('No direct script access allowed'); } |
|
4 | 4 | /** |
5 | 5 | * class EE_Request_Handler |
6 | 6 | * |
@@ -51,13 +51,13 @@ discard block |
||
51 | 51 | * @access public |
52 | 52 | * @param EE_Request $request |
53 | 53 | */ |
54 | - public function __construct( EE_Request $request ) { |
|
54 | + public function __construct(EE_Request $request) { |
|
55 | 55 | // grab request vars |
56 | 56 | $this->_params = $request->params(); |
57 | 57 | // AJAX ??? |
58 | - $this->ajax = defined( 'DOING_AJAX' ) && DOING_AJAX ? true : false; |
|
59 | - $this->front_ajax = defined( 'EE_FRONT_AJAX' ) && EE_FRONT_AJAX ? true : false; |
|
60 | - do_action( 'AHEE__EE_Request_Handler__construct__complete' ); |
|
58 | + $this->ajax = defined('DOING_AJAX') && DOING_AJAX ? true : false; |
|
59 | + $this->front_ajax = defined('EE_FRONT_AJAX') && EE_FRONT_AJAX ? true : false; |
|
60 | + do_action('AHEE__EE_Request_Handler__construct__complete'); |
|
61 | 61 | } |
62 | 62 | |
63 | 63 | |
@@ -69,12 +69,12 @@ discard block |
||
69 | 69 | * @param WP $wp |
70 | 70 | * @return void |
71 | 71 | */ |
72 | - public function parse_request( $wp = null ) { |
|
72 | + public function parse_request($wp = null) { |
|
73 | 73 | //if somebody forgot to provide us with WP, that's ok because its global |
74 | - if ( ! $wp instanceof WP ) { |
|
74 | + if ( ! $wp instanceof WP) { |
|
75 | 75 | global $wp; |
76 | 76 | } |
77 | - $this->set_request_vars( $wp ); |
|
77 | + $this->set_request_vars($wp); |
|
78 | 78 | } |
79 | 79 | |
80 | 80 | |
@@ -86,14 +86,14 @@ discard block |
||
86 | 86 | * @param WP $wp |
87 | 87 | * @return void |
88 | 88 | */ |
89 | - public function set_request_vars( $wp = null ) { |
|
90 | - if ( ! is_admin() ) { |
|
89 | + public function set_request_vars($wp = null) { |
|
90 | + if ( ! is_admin()) { |
|
91 | 91 | // set request post_id |
92 | - $this->set( 'post_id', $this->get_post_id_from_request( $wp )); |
|
92 | + $this->set('post_id', $this->get_post_id_from_request($wp)); |
|
93 | 93 | // set request post name |
94 | - $this->set( 'post_name', $this->get_post_name_from_request( $wp )); |
|
94 | + $this->set('post_name', $this->get_post_name_from_request($wp)); |
|
95 | 95 | // set request post_type |
96 | - $this->set( 'post_type', $this->get_post_type_from_request( $wp )); |
|
96 | + $this->set('post_type', $this->get_post_type_from_request($wp)); |
|
97 | 97 | // true or false ? is this page being used by EE ? |
98 | 98 | $this->set_espresso_page(); |
99 | 99 | } |
@@ -108,19 +108,19 @@ discard block |
||
108 | 108 | * @param WP $wp |
109 | 109 | * @return int |
110 | 110 | */ |
111 | - public function get_post_id_from_request( $wp = null ) { |
|
112 | - if ( ! $wp instanceof WP ){ |
|
111 | + public function get_post_id_from_request($wp = null) { |
|
112 | + if ( ! $wp instanceof WP) { |
|
113 | 113 | global $wp; |
114 | 114 | } |
115 | 115 | $post_id = null; |
116 | - if ( isset( $wp->query_vars['p'] )) { |
|
116 | + if (isset($wp->query_vars['p'])) { |
|
117 | 117 | $post_id = $wp->query_vars['p']; |
118 | 118 | } |
119 | - if ( ! $post_id && isset( $wp->query_vars['page_id'] )) { |
|
119 | + if ( ! $post_id && isset($wp->query_vars['page_id'])) { |
|
120 | 120 | $post_id = $wp->query_vars['page_id']; |
121 | 121 | } |
122 | - if ( ! $post_id && isset( $wp->request ) && is_numeric( basename( $wp->request ))) { |
|
123 | - $post_id = basename( $wp->request ); |
|
122 | + if ( ! $post_id && isset($wp->request) && is_numeric(basename($wp->request))) { |
|
123 | + $post_id = basename($wp->request); |
|
124 | 124 | } |
125 | 125 | return $post_id; |
126 | 126 | } |
@@ -134,35 +134,35 @@ discard block |
||
134 | 134 | * @param WP $wp |
135 | 135 | * @return string |
136 | 136 | */ |
137 | - public function get_post_name_from_request( $wp = null ) { |
|
138 | - if ( ! $wp instanceof WP ){ |
|
137 | + public function get_post_name_from_request($wp = null) { |
|
138 | + if ( ! $wp instanceof WP) { |
|
139 | 139 | global $wp; |
140 | 140 | } |
141 | 141 | $post_name = null; |
142 | - if ( isset( $wp->query_vars['name'] ) && ! empty( $wp->query_vars['name'] )) { |
|
142 | + if (isset($wp->query_vars['name']) && ! empty($wp->query_vars['name'])) { |
|
143 | 143 | $post_name = $wp->query_vars['name']; |
144 | 144 | } |
145 | - if ( ! $post_name && isset( $wp->query_vars['pagename'] ) && ! empty( $wp->query_vars['pagename'] )) { |
|
145 | + if ( ! $post_name && isset($wp->query_vars['pagename']) && ! empty($wp->query_vars['pagename'])) { |
|
146 | 146 | $post_name = $wp->query_vars['pagename']; |
147 | 147 | } |
148 | - if ( ! $post_name && isset( $wp->request ) && ! empty( $wp->request )) { |
|
149 | - $possible_post_name = basename( $wp->request ); |
|
150 | - if ( ! is_numeric( $possible_post_name )) { |
|
148 | + if ( ! $post_name && isset($wp->request) && ! empty($wp->request)) { |
|
149 | + $possible_post_name = basename($wp->request); |
|
150 | + if ( ! is_numeric($possible_post_name)) { |
|
151 | 151 | /** @type WPDB $wpdb */ |
152 | 152 | global $wpdb; |
153 | 153 | $SQL = "SELECT ID from {$wpdb->posts} WHERE post_status NOT IN ('auto-draft', 'inherit', 'trash') AND post_name=%s"; |
154 | - $possible_post_name = $wpdb->get_var( $wpdb->prepare( $SQL, $possible_post_name )); |
|
155 | - if ( $possible_post_name ) { |
|
154 | + $possible_post_name = $wpdb->get_var($wpdb->prepare($SQL, $possible_post_name)); |
|
155 | + if ($possible_post_name) { |
|
156 | 156 | $post_name = $possible_post_name; |
157 | 157 | } |
158 | 158 | } |
159 | 159 | } |
160 | - if ( ! $post_name && $this->get( 'post_id' )) { |
|
160 | + if ( ! $post_name && $this->get('post_id')) { |
|
161 | 161 | /** @type WPDB $wpdb */ |
162 | 162 | global $wpdb; |
163 | 163 | $SQL = "SELECT post_name from {$wpdb->posts} WHERE post_status NOT IN ('auto-draft', 'inherit', 'trash') AND ID=%d"; |
164 | - $possible_post_name = $wpdb->get_var( $wpdb->prepare( $SQL, $this->get( 'post_id' ))); |
|
165 | - if( $possible_post_name ) { |
|
164 | + $possible_post_name = $wpdb->get_var($wpdb->prepare($SQL, $this->get('post_id'))); |
|
165 | + if ($possible_post_name) { |
|
166 | 166 | $post_name = $possible_post_name; |
167 | 167 | } |
168 | 168 | } |
@@ -178,11 +178,11 @@ discard block |
||
178 | 178 | * @param WP $wp |
179 | 179 | * @return mixed |
180 | 180 | */ |
181 | - public function get_post_type_from_request( $wp = null ) { |
|
182 | - if ( ! $wp instanceof WP ){ |
|
181 | + public function get_post_type_from_request($wp = null) { |
|
182 | + if ( ! $wp instanceof WP) { |
|
183 | 183 | global $wp; |
184 | 184 | } |
185 | - return isset( $wp->query_vars['post_type'] ) ? $wp->query_vars['post_type'] : null; |
|
185 | + return isset($wp->query_vars['post_type']) ? $wp->query_vars['post_type'] : null; |
|
186 | 186 | } |
187 | 187 | |
188 | 188 | |
@@ -192,18 +192,18 @@ discard block |
||
192 | 192 | * @param WP $wp |
193 | 193 | * @return string |
194 | 194 | */ |
195 | - public function get_current_page_permalink( $wp = null ) { |
|
196 | - $post_id = $this->get_post_id_from_request( $wp ); |
|
197 | - if ( $post_id ) { |
|
198 | - $current_page_permalink = get_permalink( $post_id ); |
|
195 | + public function get_current_page_permalink($wp = null) { |
|
196 | + $post_id = $this->get_post_id_from_request($wp); |
|
197 | + if ($post_id) { |
|
198 | + $current_page_permalink = get_permalink($post_id); |
|
199 | 199 | } else { |
200 | - if ( ! $wp instanceof WP ) { |
|
200 | + if ( ! $wp instanceof WP) { |
|
201 | 201 | global $wp; |
202 | 202 | } |
203 | - if ( $wp->request ) { |
|
204 | - $current_page_permalink = site_url( $wp->request ); |
|
203 | + if ($wp->request) { |
|
204 | + $current_page_permalink = site_url($wp->request); |
|
205 | 205 | } else { |
206 | - $current_page_permalink = esc_url( site_url( $_SERVER[ 'REQUEST_URI' ] ) ); |
|
206 | + $current_page_permalink = esc_url(site_url($_SERVER['REQUEST_URI'])); |
|
207 | 207 | } |
208 | 208 | } |
209 | 209 | return $current_page_permalink; |
@@ -220,31 +220,31 @@ discard block |
||
220 | 220 | public function test_for_espresso_page() { |
221 | 221 | global $wp; |
222 | 222 | /** @type EE_CPT_Strategy $EE_CPT_Strategy */ |
223 | - $EE_CPT_Strategy = EE_Registry::instance()->load_core( 'CPT_Strategy' ); |
|
223 | + $EE_CPT_Strategy = EE_Registry::instance()->load_core('CPT_Strategy'); |
|
224 | 224 | $espresso_CPT_taxonomies = $EE_CPT_Strategy->get_CPT_taxonomies(); |
225 | - if ( is_array( $espresso_CPT_taxonomies ) ) { |
|
226 | - foreach ( $espresso_CPT_taxonomies as $espresso_CPT_taxonomy =>$details ) { |
|
227 | - if ( isset( $wp->query_vars, $wp->query_vars[ $espresso_CPT_taxonomy ] ) ) { |
|
225 | + if (is_array($espresso_CPT_taxonomies)) { |
|
226 | + foreach ($espresso_CPT_taxonomies as $espresso_CPT_taxonomy =>$details) { |
|
227 | + if (isset($wp->query_vars, $wp->query_vars[$espresso_CPT_taxonomy])) { |
|
228 | 228 | return true; |
229 | 229 | } |
230 | 230 | } |
231 | 231 | } |
232 | 232 | // load espresso CPT endpoints |
233 | 233 | $espresso_CPT_endpoints = $EE_CPT_Strategy->get_CPT_endpoints(); |
234 | - $post_type_CPT_endpoints = array_flip( $espresso_CPT_endpoints ); |
|
235 | - $post_types = (array)$this->get( 'post_type' ); |
|
236 | - foreach ( $post_types as $post_type ) { |
|
234 | + $post_type_CPT_endpoints = array_flip($espresso_CPT_endpoints); |
|
235 | + $post_types = (array) $this->get('post_type'); |
|
236 | + foreach ($post_types as $post_type) { |
|
237 | 237 | // was a post name passed ? |
238 | - if ( isset( $post_type_CPT_endpoints[ $post_type ] ) ) { |
|
238 | + if (isset($post_type_CPT_endpoints[$post_type])) { |
|
239 | 239 | // kk we know this is an espresso page, but is it a specific post ? |
240 | - if ( ! $this->get( 'post_name' ) ) { |
|
240 | + if ( ! $this->get('post_name')) { |
|
241 | 241 | // there's no specific post name set, so maybe it's one of our endpoints like www.domain.com/events |
242 | - $post_name = isset( $post_type_CPT_endpoints[ $this->get( 'post_type' ) ] ) |
|
243 | - ? $post_type_CPT_endpoints[ $this->get( 'post_type' ) ] |
|
242 | + $post_name = isset($post_type_CPT_endpoints[$this->get('post_type')]) |
|
243 | + ? $post_type_CPT_endpoints[$this->get('post_type')] |
|
244 | 244 | : ''; |
245 | 245 | // if the post type matches on of our then set the endpoint |
246 | - if ( $post_name ) { |
|
247 | - $this->set( 'post_name', $post_name ); |
|
246 | + if ($post_name) { |
|
247 | + $this->set('post_name', $post_name); |
|
248 | 248 | } |
249 | 249 | } |
250 | 250 | return true; |
@@ -262,7 +262,7 @@ discard block |
||
262 | 262 | * @param null|bool $value |
263 | 263 | * @return void |
264 | 264 | */ |
265 | - public function set_espresso_page( $value = null ) { |
|
265 | + public function set_espresso_page($value = null) { |
|
266 | 266 | $this->_params['is_espresso_page'] = ! empty($value) ? $value : $this->test_for_espresso_page(); |
267 | 267 | } |
268 | 268 | |
@@ -275,7 +275,7 @@ discard block |
||
275 | 275 | * @return mixed |
276 | 276 | */ |
277 | 277 | public function is_espresso_page() { |
278 | - return isset( $this->_params['is_espresso_page'] ) ? $this->_params['is_espresso_page'] : false; |
|
278 | + return isset($this->_params['is_espresso_page']) ? $this->_params['is_espresso_page'] : false; |
|
279 | 279 | } |
280 | 280 | |
281 | 281 | |
@@ -299,14 +299,14 @@ discard block |
||
299 | 299 | * @param bool $override_ee |
300 | 300 | * @return void |
301 | 301 | */ |
302 | - public function set( $key, $value, $override_ee = false ) { |
|
302 | + public function set($key, $value, $override_ee = false) { |
|
303 | 303 | // don't allow "ee" to be overwritten unless explicitly instructed to do so |
304 | 304 | if ( |
305 | 305 | $key !== 'ee' || |
306 | - ( $key === 'ee' && empty( $this->_params['ee'] )) |
|
307 | - || ( $key === 'ee' && ! empty( $this->_params['ee'] ) && $override_ee ) |
|
306 | + ($key === 'ee' && empty($this->_params['ee'])) |
|
307 | + || ($key === 'ee' && ! empty($this->_params['ee']) && $override_ee) |
|
308 | 308 | ) { |
309 | - $this->_params[ $key ] = $value; |
|
309 | + $this->_params[$key] = $value; |
|
310 | 310 | } |
311 | 311 | } |
312 | 312 | |
@@ -320,8 +320,8 @@ discard block |
||
320 | 320 | * @param null $default |
321 | 321 | * @return mixed |
322 | 322 | */ |
323 | - public function get( $key, $default = null ) { |
|
324 | - return isset( $this->_params[ $key ] ) ? $this->_params[ $key ] : $default; |
|
323 | + public function get($key, $default = null) { |
|
324 | + return isset($this->_params[$key]) ? $this->_params[$key] : $default; |
|
325 | 325 | } |
326 | 326 | |
327 | 327 | |
@@ -333,8 +333,8 @@ discard block |
||
333 | 333 | * @param $key |
334 | 334 | * @return boolean |
335 | 335 | */ |
336 | - public function is_set( $key ) { |
|
337 | - return isset( $this->_params[ $key ] ) ? true : false; |
|
336 | + public function is_set($key) { |
|
337 | + return isset($this->_params[$key]) ? true : false; |
|
338 | 338 | } |
339 | 339 | |
340 | 340 | |
@@ -346,8 +346,8 @@ discard block |
||
346 | 346 | * @param $key |
347 | 347 | * @return void |
348 | 348 | */ |
349 | - public function un_set( $key ) { |
|
350 | - unset( $this->_params[ $key ] ); |
|
349 | + public function un_set($key) { |
|
350 | + unset($this->_params[$key]); |
|
351 | 351 | } |
352 | 352 | |
353 | 353 | |
@@ -360,8 +360,8 @@ discard block |
||
360 | 360 | * @param $value |
361 | 361 | * @return void |
362 | 362 | */ |
363 | - public function set_notice( $key, $value ) { |
|
364 | - $this->_notice[ $key ] = $value; |
|
363 | + public function set_notice($key, $value) { |
|
364 | + $this->_notice[$key] = $value; |
|
365 | 365 | } |
366 | 366 | |
367 | 367 | |
@@ -373,8 +373,8 @@ discard block |
||
373 | 373 | * @param $key |
374 | 374 | * @return mixed |
375 | 375 | */ |
376 | - public function get_notice( $key ) { |
|
377 | - return isset( $this->_notice[ $key ] ) ? $this->_notice[ $key ] : null; |
|
376 | + public function get_notice($key) { |
|
377 | + return isset($this->_notice[$key]) ? $this->_notice[$key] : null; |
|
378 | 378 | } |
379 | 379 | |
380 | 380 | |
@@ -386,7 +386,7 @@ discard block |
||
386 | 386 | * @param $string |
387 | 387 | * @return void |
388 | 388 | */ |
389 | - public function add_output( $string ) { |
|
389 | + public function add_output($string) { |
|
390 | 390 | $this->_output .= $string; |
391 | 391 | } |
392 | 392 | |
@@ -408,8 +408,8 @@ discard block |
||
408 | 408 | * @param $item |
409 | 409 | * @param $key |
410 | 410 | */ |
411 | - public function sanitize_text_field_for_array_walk( &$item, &$key ) { |
|
412 | - $item = strpos( $item, 'email' ) !== false ? sanitize_email( $item ) : sanitize_text_field( $item ); |
|
411 | + public function sanitize_text_field_for_array_walk(&$item, &$key) { |
|
412 | + $item = strpos($item, 'email') !== false ? sanitize_email($item) : sanitize_text_field($item); |
|
413 | 413 | } |
414 | 414 | |
415 | 415 | |
@@ -419,7 +419,7 @@ discard block |
||
419 | 419 | * @param $b |
420 | 420 | * @return bool |
421 | 421 | */ |
422 | - public function __set($a,$b) { return false; } |
|
422 | + public function __set($a, $b) { return false; } |
|
423 | 423 | |
424 | 424 | |
425 | 425 |
@@ -17,316 +17,316 @@ |
||
17 | 17 | final class EE_Module_Request_Router implements InterminableInterface |
18 | 18 | { |
19 | 19 | |
20 | - /** |
|
21 | - * @var array $_previous_routes |
|
22 | - */ |
|
23 | - private static $_previous_routes = array(); |
|
24 | - |
|
25 | - /** |
|
26 | - * @var WP_Query $WP_Query |
|
27 | - */ |
|
28 | - public $WP_Query; |
|
29 | - |
|
30 | - |
|
31 | - |
|
32 | - /** |
|
33 | - * EE_Module_Request_Router constructor. |
|
34 | - */ |
|
35 | - public function __construct() |
|
36 | - { |
|
37 | - } |
|
38 | - |
|
39 | - |
|
40 | - |
|
41 | - /** |
|
42 | - * on the first call to this method, it checks the EE_Request_Handler for a "route" |
|
43 | - * on subsequent calls to this method, |
|
44 | - * instead of checking the EE_Request_Handler for a route, it checks the previous routes array, |
|
45 | - * and checks if the last called route has any forwarding routes registered for it |
|
46 | - * |
|
47 | - * @param WP_Query $WP_Query |
|
48 | - * @return NULL|string |
|
49 | - * @throws EE_Error |
|
50 | - * @throws ReflectionException |
|
51 | - */ |
|
52 | - public function get_route(WP_Query $WP_Query) |
|
53 | - { |
|
54 | - $this->WP_Query = $WP_Query; |
|
55 | - // assume this if first route being called |
|
56 | - $previous_route = false; |
|
57 | - // but is it really ??? |
|
58 | - if (! empty(self::$_previous_routes)) { |
|
59 | - // get last run route |
|
60 | - $previous_routes = array_values(self::$_previous_routes); |
|
61 | - $previous_route = array_pop($previous_routes); |
|
62 | - } |
|
63 | - // has another route already been run ? |
|
64 | - if ($previous_route) { |
|
65 | - // check if forwarding has been set |
|
66 | - $current_route = $this->get_forward($previous_route); |
|
67 | - try { |
|
68 | - //check for recursive forwarding |
|
69 | - if (isset(self::$_previous_routes[$current_route])) { |
|
70 | - throw new EE_Error( |
|
71 | - sprintf( |
|
72 | - __( |
|
73 | - 'An error occurred. The %s route has already been called, and therefore can not be forwarded to, because an infinite loop would be created and break the interweb.', |
|
74 | - 'event_espresso' |
|
75 | - ), |
|
76 | - $current_route |
|
77 | - ) |
|
78 | - ); |
|
79 | - } |
|
80 | - } catch (EE_Error $e) { |
|
81 | - $e->get_error(); |
|
82 | - return null; |
|
83 | - } |
|
84 | - } else { |
|
85 | - // first route called |
|
86 | - $current_route = null; |
|
87 | - // grab all routes |
|
88 | - $routes = EE_Config::get_routes(); |
|
89 | - //d( $routes ); |
|
90 | - foreach ($routes as $key => $route) { |
|
91 | - // check request for module route |
|
92 | - if (EE_Registry::instance()->REQ->is_set($key)) { |
|
93 | - //echo '<b style="color:#2EA2CC;">key : <span style="color:#E76700">' . $key . '</span></b><br />'; |
|
94 | - $current_route = sanitize_text_field(EE_Registry::instance()->REQ->get($key)); |
|
95 | - if ($current_route) { |
|
96 | - $current_route = array($key, $current_route); |
|
97 | - //echo '<b style="color:#2EA2CC;">current_route : <span style="color:#E76700">' . $current_route . '</span></b><br />'; |
|
98 | - break; |
|
99 | - } |
|
100 | - } |
|
101 | - } |
|
102 | - } |
|
103 | - // sorry, but I can't read what you route ! |
|
104 | - if (empty($current_route)) { |
|
105 | - return null; |
|
106 | - } |
|
107 | - //add route to previous routes array |
|
108 | - self::$_previous_routes[] = $current_route; |
|
109 | - return $current_route; |
|
110 | - } |
|
111 | - |
|
112 | - |
|
113 | - |
|
114 | - /** |
|
115 | - * this method simply takes a valid route, and resolves what module class method the route points to |
|
116 | - * |
|
117 | - * @param string $key |
|
118 | - * @param string $current_route |
|
119 | - * @return mixed EED_Module | boolean |
|
120 | - * @throws EE_Error |
|
121 | - * @throws ReflectionException |
|
122 | - */ |
|
123 | - public function resolve_route($key, $current_route) |
|
124 | - { |
|
125 | - // get module method that route has been mapped to |
|
126 | - $module_method = EE_Config::get_route($current_route, $key); |
|
127 | - //EEH_Debug_Tools::printr( $module_method, '$module_method <br /><span style="font-size:10px;font-weight:normal;">' . __FILE__ . '<br />line no: ' . __LINE__ . '</span>', 'auto' ); |
|
128 | - // verify result was returned |
|
129 | - if (empty($module_method)) { |
|
130 | - $msg = sprintf( |
|
131 | - __('The requested route %s could not be mapped to any registered modules.', 'event_espresso'), |
|
132 | - $current_route |
|
133 | - ); |
|
134 | - EE_Error::add_error($msg, __FILE__, __FUNCTION__, __LINE__); |
|
135 | - return false; |
|
136 | - } |
|
137 | - // verify that result is an array |
|
138 | - if (! is_array($module_method)) { |
|
139 | - $msg = sprintf(__('The %s route has not been properly registered.', 'event_espresso'), $current_route); |
|
140 | - EE_Error::add_error($msg . '||' . $msg, __FILE__, __FUNCTION__, __LINE__); |
|
141 | - return false; |
|
142 | - } |
|
143 | - // grab module name |
|
144 | - $module_name = $module_method[0]; |
|
145 | - // verify that a class method was registered properly |
|
146 | - if (! isset($module_method[1])) { |
|
147 | - $msg = sprintf( |
|
148 | - __('A class method for the %s route has not been properly registered.', 'event_espresso'), |
|
149 | - $current_route |
|
150 | - ); |
|
151 | - EE_Error::add_error($msg . '||' . $msg, __FILE__, __FUNCTION__, __LINE__); |
|
152 | - return false; |
|
153 | - } |
|
154 | - // grab method |
|
155 | - $method = $module_method[1]; |
|
156 | - // verify that class exists |
|
157 | - if (! class_exists($module_name)) { |
|
158 | - $msg = sprintf(__('The requested %s class could not be found.', 'event_espresso'), $module_name); |
|
159 | - EE_Error::add_error($msg, __FILE__, __FUNCTION__, __LINE__); |
|
160 | - return false; |
|
161 | - } |
|
162 | - // verify that method exists |
|
163 | - if (! method_exists($module_name, $method)) { |
|
164 | - $msg = sprintf( |
|
165 | - __('The class method %s for the %s route is in invalid.', 'event_espresso'), $method, $current_route |
|
166 | - ); |
|
167 | - EE_Error::add_error($msg . '||' . $msg, __FILE__, __FUNCTION__, __LINE__); |
|
168 | - return false; |
|
169 | - } |
|
170 | - // instantiate module and call route method |
|
171 | - return $this->_module_router($module_name, $method); |
|
172 | - } |
|
173 | - |
|
174 | - |
|
175 | - |
|
176 | - /** |
|
177 | - * this method instantiates modules and calls the method that was defined when the route was registered |
|
178 | - * |
|
179 | - * @param string $module_name |
|
180 | - * @return EED_Module|object|null |
|
181 | - * @throws ReflectionException |
|
182 | - */ |
|
183 | - public static function module_factory($module_name) |
|
184 | - { |
|
185 | - if ($module_name === 'EED_Module') { |
|
186 | - EE_Error::add_error( |
|
187 | - sprintf( |
|
188 | - __( |
|
189 | - 'EED_Module is an abstract parent class an can not be instantiated. Please provide a proper module name.', |
|
190 | - 'event_espresso' |
|
191 | - ), $module_name |
|
192 | - ), __FILE__, __FUNCTION__, __LINE__ |
|
193 | - ); |
|
194 | - return null; |
|
195 | - } |
|
196 | - // let's pause to reflect on this... |
|
197 | - $mod_reflector = new ReflectionClass($module_name); |
|
198 | - // ensure that class is actually a module |
|
199 | - if (! $mod_reflector->isSubclassOf('EED_Module')) { |
|
200 | - EE_Error::add_error( |
|
201 | - sprintf(__('The requested %s module is not of the class EED_Module.', 'event_espresso'), $module_name), |
|
202 | - __FILE__, __FUNCTION__, __LINE__ |
|
203 | - ); |
|
204 | - return null; |
|
205 | - } |
|
206 | - // instantiate and return module class |
|
207 | - return $mod_reflector->newInstance(); |
|
208 | - } |
|
209 | - |
|
210 | - |
|
211 | - |
|
212 | - /** |
|
213 | - * this method instantiates modules and calls the method that was defined when the route was registered |
|
214 | - * |
|
215 | - * @param string $module_name |
|
216 | - * @param string $method |
|
217 | - * @return EED_Module|null |
|
218 | - * @throws EE_Error |
|
219 | - * @throws ReflectionException |
|
220 | - */ |
|
221 | - private function _module_router($module_name, $method) |
|
222 | - { |
|
223 | - // instantiate module class |
|
224 | - $module = EE_Module_Request_Router::module_factory($module_name); |
|
225 | - if ($module instanceof EED_Module) { |
|
226 | - // and call whatever action the route was for |
|
227 | - try { |
|
228 | - call_user_func(array($module, $method), $this->WP_Query); |
|
229 | - } catch (EE_Error $e) { |
|
230 | - $e->get_error(); |
|
231 | - return null; |
|
232 | - } |
|
233 | - } |
|
234 | - return $module; |
|
235 | - } |
|
236 | - |
|
237 | - |
|
238 | - |
|
239 | - /** |
|
240 | - * @param $current_route |
|
241 | - * @return string |
|
242 | - */ |
|
243 | - public function get_forward($current_route) |
|
244 | - { |
|
245 | - return EE_Config::get_forward($current_route); |
|
246 | - } |
|
247 | - |
|
248 | - |
|
249 | - |
|
250 | - /** |
|
251 | - * @param $current_route |
|
252 | - * @return string |
|
253 | - */ |
|
254 | - public function get_view($current_route) |
|
255 | - { |
|
256 | - return EE_Config::get_view($current_route); |
|
257 | - } |
|
258 | - |
|
259 | - |
|
260 | - |
|
261 | - /** |
|
262 | - * @param $a |
|
263 | - * @param $b |
|
264 | - * @return bool |
|
265 | - */ |
|
266 | - public function __set($a, $b) |
|
267 | - { |
|
268 | - return false; |
|
269 | - } |
|
270 | - |
|
271 | - |
|
272 | - |
|
273 | - /** |
|
274 | - * @param $a |
|
275 | - * @return bool |
|
276 | - */ |
|
277 | - public function __get($a) |
|
278 | - { |
|
279 | - return false; |
|
280 | - } |
|
281 | - |
|
282 | - |
|
283 | - |
|
284 | - /** |
|
285 | - * @param $a |
|
286 | - * @return bool |
|
287 | - */ |
|
288 | - public function __isset($a) |
|
289 | - { |
|
290 | - return false; |
|
291 | - } |
|
292 | - |
|
293 | - |
|
294 | - |
|
295 | - /** |
|
296 | - * @param $a |
|
297 | - * @return bool |
|
298 | - */ |
|
299 | - public function __unset($a) |
|
300 | - { |
|
301 | - return false; |
|
302 | - } |
|
303 | - |
|
304 | - |
|
305 | - |
|
306 | - /** |
|
307 | - * @return void |
|
308 | - */ |
|
309 | - public function __clone() |
|
310 | - { |
|
311 | - } |
|
312 | - |
|
313 | - |
|
314 | - |
|
315 | - /** |
|
316 | - * @return void |
|
317 | - */ |
|
318 | - public function __wakeup() |
|
319 | - { |
|
320 | - } |
|
20 | + /** |
|
21 | + * @var array $_previous_routes |
|
22 | + */ |
|
23 | + private static $_previous_routes = array(); |
|
24 | + |
|
25 | + /** |
|
26 | + * @var WP_Query $WP_Query |
|
27 | + */ |
|
28 | + public $WP_Query; |
|
29 | + |
|
30 | + |
|
31 | + |
|
32 | + /** |
|
33 | + * EE_Module_Request_Router constructor. |
|
34 | + */ |
|
35 | + public function __construct() |
|
36 | + { |
|
37 | + } |
|
38 | + |
|
39 | + |
|
40 | + |
|
41 | + /** |
|
42 | + * on the first call to this method, it checks the EE_Request_Handler for a "route" |
|
43 | + * on subsequent calls to this method, |
|
44 | + * instead of checking the EE_Request_Handler for a route, it checks the previous routes array, |
|
45 | + * and checks if the last called route has any forwarding routes registered for it |
|
46 | + * |
|
47 | + * @param WP_Query $WP_Query |
|
48 | + * @return NULL|string |
|
49 | + * @throws EE_Error |
|
50 | + * @throws ReflectionException |
|
51 | + */ |
|
52 | + public function get_route(WP_Query $WP_Query) |
|
53 | + { |
|
54 | + $this->WP_Query = $WP_Query; |
|
55 | + // assume this if first route being called |
|
56 | + $previous_route = false; |
|
57 | + // but is it really ??? |
|
58 | + if (! empty(self::$_previous_routes)) { |
|
59 | + // get last run route |
|
60 | + $previous_routes = array_values(self::$_previous_routes); |
|
61 | + $previous_route = array_pop($previous_routes); |
|
62 | + } |
|
63 | + // has another route already been run ? |
|
64 | + if ($previous_route) { |
|
65 | + // check if forwarding has been set |
|
66 | + $current_route = $this->get_forward($previous_route); |
|
67 | + try { |
|
68 | + //check for recursive forwarding |
|
69 | + if (isset(self::$_previous_routes[$current_route])) { |
|
70 | + throw new EE_Error( |
|
71 | + sprintf( |
|
72 | + __( |
|
73 | + 'An error occurred. The %s route has already been called, and therefore can not be forwarded to, because an infinite loop would be created and break the interweb.', |
|
74 | + 'event_espresso' |
|
75 | + ), |
|
76 | + $current_route |
|
77 | + ) |
|
78 | + ); |
|
79 | + } |
|
80 | + } catch (EE_Error $e) { |
|
81 | + $e->get_error(); |
|
82 | + return null; |
|
83 | + } |
|
84 | + } else { |
|
85 | + // first route called |
|
86 | + $current_route = null; |
|
87 | + // grab all routes |
|
88 | + $routes = EE_Config::get_routes(); |
|
89 | + //d( $routes ); |
|
90 | + foreach ($routes as $key => $route) { |
|
91 | + // check request for module route |
|
92 | + if (EE_Registry::instance()->REQ->is_set($key)) { |
|
93 | + //echo '<b style="color:#2EA2CC;">key : <span style="color:#E76700">' . $key . '</span></b><br />'; |
|
94 | + $current_route = sanitize_text_field(EE_Registry::instance()->REQ->get($key)); |
|
95 | + if ($current_route) { |
|
96 | + $current_route = array($key, $current_route); |
|
97 | + //echo '<b style="color:#2EA2CC;">current_route : <span style="color:#E76700">' . $current_route . '</span></b><br />'; |
|
98 | + break; |
|
99 | + } |
|
100 | + } |
|
101 | + } |
|
102 | + } |
|
103 | + // sorry, but I can't read what you route ! |
|
104 | + if (empty($current_route)) { |
|
105 | + return null; |
|
106 | + } |
|
107 | + //add route to previous routes array |
|
108 | + self::$_previous_routes[] = $current_route; |
|
109 | + return $current_route; |
|
110 | + } |
|
111 | + |
|
112 | + |
|
113 | + |
|
114 | + /** |
|
115 | + * this method simply takes a valid route, and resolves what module class method the route points to |
|
116 | + * |
|
117 | + * @param string $key |
|
118 | + * @param string $current_route |
|
119 | + * @return mixed EED_Module | boolean |
|
120 | + * @throws EE_Error |
|
121 | + * @throws ReflectionException |
|
122 | + */ |
|
123 | + public function resolve_route($key, $current_route) |
|
124 | + { |
|
125 | + // get module method that route has been mapped to |
|
126 | + $module_method = EE_Config::get_route($current_route, $key); |
|
127 | + //EEH_Debug_Tools::printr( $module_method, '$module_method <br /><span style="font-size:10px;font-weight:normal;">' . __FILE__ . '<br />line no: ' . __LINE__ . '</span>', 'auto' ); |
|
128 | + // verify result was returned |
|
129 | + if (empty($module_method)) { |
|
130 | + $msg = sprintf( |
|
131 | + __('The requested route %s could not be mapped to any registered modules.', 'event_espresso'), |
|
132 | + $current_route |
|
133 | + ); |
|
134 | + EE_Error::add_error($msg, __FILE__, __FUNCTION__, __LINE__); |
|
135 | + return false; |
|
136 | + } |
|
137 | + // verify that result is an array |
|
138 | + if (! is_array($module_method)) { |
|
139 | + $msg = sprintf(__('The %s route has not been properly registered.', 'event_espresso'), $current_route); |
|
140 | + EE_Error::add_error($msg . '||' . $msg, __FILE__, __FUNCTION__, __LINE__); |
|
141 | + return false; |
|
142 | + } |
|
143 | + // grab module name |
|
144 | + $module_name = $module_method[0]; |
|
145 | + // verify that a class method was registered properly |
|
146 | + if (! isset($module_method[1])) { |
|
147 | + $msg = sprintf( |
|
148 | + __('A class method for the %s route has not been properly registered.', 'event_espresso'), |
|
149 | + $current_route |
|
150 | + ); |
|
151 | + EE_Error::add_error($msg . '||' . $msg, __FILE__, __FUNCTION__, __LINE__); |
|
152 | + return false; |
|
153 | + } |
|
154 | + // grab method |
|
155 | + $method = $module_method[1]; |
|
156 | + // verify that class exists |
|
157 | + if (! class_exists($module_name)) { |
|
158 | + $msg = sprintf(__('The requested %s class could not be found.', 'event_espresso'), $module_name); |
|
159 | + EE_Error::add_error($msg, __FILE__, __FUNCTION__, __LINE__); |
|
160 | + return false; |
|
161 | + } |
|
162 | + // verify that method exists |
|
163 | + if (! method_exists($module_name, $method)) { |
|
164 | + $msg = sprintf( |
|
165 | + __('The class method %s for the %s route is in invalid.', 'event_espresso'), $method, $current_route |
|
166 | + ); |
|
167 | + EE_Error::add_error($msg . '||' . $msg, __FILE__, __FUNCTION__, __LINE__); |
|
168 | + return false; |
|
169 | + } |
|
170 | + // instantiate module and call route method |
|
171 | + return $this->_module_router($module_name, $method); |
|
172 | + } |
|
173 | + |
|
174 | + |
|
175 | + |
|
176 | + /** |
|
177 | + * this method instantiates modules and calls the method that was defined when the route was registered |
|
178 | + * |
|
179 | + * @param string $module_name |
|
180 | + * @return EED_Module|object|null |
|
181 | + * @throws ReflectionException |
|
182 | + */ |
|
183 | + public static function module_factory($module_name) |
|
184 | + { |
|
185 | + if ($module_name === 'EED_Module') { |
|
186 | + EE_Error::add_error( |
|
187 | + sprintf( |
|
188 | + __( |
|
189 | + 'EED_Module is an abstract parent class an can not be instantiated. Please provide a proper module name.', |
|
190 | + 'event_espresso' |
|
191 | + ), $module_name |
|
192 | + ), __FILE__, __FUNCTION__, __LINE__ |
|
193 | + ); |
|
194 | + return null; |
|
195 | + } |
|
196 | + // let's pause to reflect on this... |
|
197 | + $mod_reflector = new ReflectionClass($module_name); |
|
198 | + // ensure that class is actually a module |
|
199 | + if (! $mod_reflector->isSubclassOf('EED_Module')) { |
|
200 | + EE_Error::add_error( |
|
201 | + sprintf(__('The requested %s module is not of the class EED_Module.', 'event_espresso'), $module_name), |
|
202 | + __FILE__, __FUNCTION__, __LINE__ |
|
203 | + ); |
|
204 | + return null; |
|
205 | + } |
|
206 | + // instantiate and return module class |
|
207 | + return $mod_reflector->newInstance(); |
|
208 | + } |
|
209 | + |
|
210 | + |
|
211 | + |
|
212 | + /** |
|
213 | + * this method instantiates modules and calls the method that was defined when the route was registered |
|
214 | + * |
|
215 | + * @param string $module_name |
|
216 | + * @param string $method |
|
217 | + * @return EED_Module|null |
|
218 | + * @throws EE_Error |
|
219 | + * @throws ReflectionException |
|
220 | + */ |
|
221 | + private function _module_router($module_name, $method) |
|
222 | + { |
|
223 | + // instantiate module class |
|
224 | + $module = EE_Module_Request_Router::module_factory($module_name); |
|
225 | + if ($module instanceof EED_Module) { |
|
226 | + // and call whatever action the route was for |
|
227 | + try { |
|
228 | + call_user_func(array($module, $method), $this->WP_Query); |
|
229 | + } catch (EE_Error $e) { |
|
230 | + $e->get_error(); |
|
231 | + return null; |
|
232 | + } |
|
233 | + } |
|
234 | + return $module; |
|
235 | + } |
|
236 | + |
|
237 | + |
|
238 | + |
|
239 | + /** |
|
240 | + * @param $current_route |
|
241 | + * @return string |
|
242 | + */ |
|
243 | + public function get_forward($current_route) |
|
244 | + { |
|
245 | + return EE_Config::get_forward($current_route); |
|
246 | + } |
|
247 | + |
|
248 | + |
|
249 | + |
|
250 | + /** |
|
251 | + * @param $current_route |
|
252 | + * @return string |
|
253 | + */ |
|
254 | + public function get_view($current_route) |
|
255 | + { |
|
256 | + return EE_Config::get_view($current_route); |
|
257 | + } |
|
258 | + |
|
259 | + |
|
260 | + |
|
261 | + /** |
|
262 | + * @param $a |
|
263 | + * @param $b |
|
264 | + * @return bool |
|
265 | + */ |
|
266 | + public function __set($a, $b) |
|
267 | + { |
|
268 | + return false; |
|
269 | + } |
|
270 | + |
|
271 | + |
|
272 | + |
|
273 | + /** |
|
274 | + * @param $a |
|
275 | + * @return bool |
|
276 | + */ |
|
277 | + public function __get($a) |
|
278 | + { |
|
279 | + return false; |
|
280 | + } |
|
281 | + |
|
282 | + |
|
283 | + |
|
284 | + /** |
|
285 | + * @param $a |
|
286 | + * @return bool |
|
287 | + */ |
|
288 | + public function __isset($a) |
|
289 | + { |
|
290 | + return false; |
|
291 | + } |
|
292 | + |
|
293 | + |
|
294 | + |
|
295 | + /** |
|
296 | + * @param $a |
|
297 | + * @return bool |
|
298 | + */ |
|
299 | + public function __unset($a) |
|
300 | + { |
|
301 | + return false; |
|
302 | + } |
|
303 | + |
|
304 | + |
|
305 | + |
|
306 | + /** |
|
307 | + * @return void |
|
308 | + */ |
|
309 | + public function __clone() |
|
310 | + { |
|
311 | + } |
|
312 | + |
|
313 | + |
|
314 | + |
|
315 | + /** |
|
316 | + * @return void |
|
317 | + */ |
|
318 | + public function __wakeup() |
|
319 | + { |
|
320 | + } |
|
321 | 321 | |
322 | 322 | |
323 | 323 | |
324 | - /** |
|
325 | - * |
|
326 | - */ |
|
327 | - public function __destruct() |
|
328 | - { |
|
329 | - } |
|
324 | + /** |
|
325 | + * |
|
326 | + */ |
|
327 | + public function __destruct() |
|
328 | + { |
|
329 | + } |
|
330 | 330 | |
331 | 331 | } |
332 | 332 | // End of file EE_Module_Request_Router.core.php |
@@ -55,7 +55,7 @@ discard block |
||
55 | 55 | // assume this if first route being called |
56 | 56 | $previous_route = false; |
57 | 57 | // but is it really ??? |
58 | - if (! empty(self::$_previous_routes)) { |
|
58 | + if ( ! empty(self::$_previous_routes)) { |
|
59 | 59 | // get last run route |
60 | 60 | $previous_routes = array_values(self::$_previous_routes); |
61 | 61 | $previous_route = array_pop($previous_routes); |
@@ -135,36 +135,36 @@ discard block |
||
135 | 135 | return false; |
136 | 136 | } |
137 | 137 | // verify that result is an array |
138 | - if (! is_array($module_method)) { |
|
138 | + if ( ! is_array($module_method)) { |
|
139 | 139 | $msg = sprintf(__('The %s route has not been properly registered.', 'event_espresso'), $current_route); |
140 | - EE_Error::add_error($msg . '||' . $msg, __FILE__, __FUNCTION__, __LINE__); |
|
140 | + EE_Error::add_error($msg.'||'.$msg, __FILE__, __FUNCTION__, __LINE__); |
|
141 | 141 | return false; |
142 | 142 | } |
143 | 143 | // grab module name |
144 | 144 | $module_name = $module_method[0]; |
145 | 145 | // verify that a class method was registered properly |
146 | - if (! isset($module_method[1])) { |
|
146 | + if ( ! isset($module_method[1])) { |
|
147 | 147 | $msg = sprintf( |
148 | 148 | __('A class method for the %s route has not been properly registered.', 'event_espresso'), |
149 | 149 | $current_route |
150 | 150 | ); |
151 | - EE_Error::add_error($msg . '||' . $msg, __FILE__, __FUNCTION__, __LINE__); |
|
151 | + EE_Error::add_error($msg.'||'.$msg, __FILE__, __FUNCTION__, __LINE__); |
|
152 | 152 | return false; |
153 | 153 | } |
154 | 154 | // grab method |
155 | 155 | $method = $module_method[1]; |
156 | 156 | // verify that class exists |
157 | - if (! class_exists($module_name)) { |
|
157 | + if ( ! class_exists($module_name)) { |
|
158 | 158 | $msg = sprintf(__('The requested %s class could not be found.', 'event_espresso'), $module_name); |
159 | 159 | EE_Error::add_error($msg, __FILE__, __FUNCTION__, __LINE__); |
160 | 160 | return false; |
161 | 161 | } |
162 | 162 | // verify that method exists |
163 | - if (! method_exists($module_name, $method)) { |
|
163 | + if ( ! method_exists($module_name, $method)) { |
|
164 | 164 | $msg = sprintf( |
165 | 165 | __('The class method %s for the %s route is in invalid.', 'event_espresso'), $method, $current_route |
166 | 166 | ); |
167 | - EE_Error::add_error($msg . '||' . $msg, __FILE__, __FUNCTION__, __LINE__); |
|
167 | + EE_Error::add_error($msg.'||'.$msg, __FILE__, __FUNCTION__, __LINE__); |
|
168 | 168 | return false; |
169 | 169 | } |
170 | 170 | // instantiate module and call route method |
@@ -196,7 +196,7 @@ discard block |
||
196 | 196 | // let's pause to reflect on this... |
197 | 197 | $mod_reflector = new ReflectionClass($module_name); |
198 | 198 | // ensure that class is actually a module |
199 | - if (! $mod_reflector->isSubclassOf('EED_Module')) { |
|
199 | + if ( ! $mod_reflector->isSubclassOf('EED_Module')) { |
|
200 | 200 | EE_Error::add_error( |
201 | 201 | sprintf(__('The requested %s module is not of the class EED_Module.', 'event_espresso'), $module_name), |
202 | 202 | __FILE__, __FUNCTION__, __LINE__ |
@@ -2,7 +2,7 @@ discard block |
||
2 | 2 | use EventEspresso\core\interfaces\ResettableInterface; |
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 | do_action('AHEE_log', __FILE__, __FUNCTION__, ''); |
8 | 8 | |
@@ -23,418 +23,418 @@ discard block |
||
23 | 23 | class EE_Cart implements ResettableInterface |
24 | 24 | { |
25 | 25 | |
26 | - /** |
|
27 | - * instance of the EE_Cart object |
|
28 | - * |
|
29 | - * @access private |
|
30 | - * @var EE_Cart $_instance |
|
31 | - */ |
|
32 | - private static $_instance; |
|
33 | - |
|
34 | - /** |
|
35 | - * instance of the EE_Session object |
|
36 | - * |
|
37 | - * @access protected |
|
38 | - * @var EE_Session $_session |
|
39 | - */ |
|
40 | - protected $_session; |
|
41 | - |
|
42 | - /** |
|
43 | - * The total Line item which comprises all the children line-item subtotals, |
|
44 | - * which in turn each have their line items. |
|
45 | - * Typically, the line item structure will look like: |
|
46 | - * grand total |
|
47 | - * -tickets-sub-total |
|
48 | - * --ticket1 |
|
49 | - * --ticket2 |
|
50 | - * --... |
|
51 | - * -taxes-sub-total |
|
52 | - * --tax1 |
|
53 | - * --tax2 |
|
54 | - * |
|
55 | - * @var EE_Line_Item |
|
56 | - */ |
|
57 | - private $_grand_total; |
|
58 | - |
|
59 | - |
|
60 | - |
|
61 | - /** |
|
62 | - * @singleton method used to instantiate class object |
|
63 | - * @access public |
|
64 | - * @param EE_Line_Item $grand_total |
|
65 | - * @param EE_Session $session |
|
66 | - * @return \EE_Cart |
|
67 | - * @throws \EE_Error |
|
68 | - */ |
|
69 | - public static function instance(EE_Line_Item $grand_total = null, EE_Session $session = null) |
|
70 | - { |
|
71 | - if ( ! empty($grand_total)) { |
|
72 | - self::$_instance = new self($grand_total, $session); |
|
73 | - } |
|
74 | - // or maybe retrieve an existing one ? |
|
75 | - if ( ! self::$_instance instanceof EE_Cart) { |
|
76 | - // try getting the cart out of the session |
|
77 | - $saved_cart = $session instanceof EE_Session ? $session->cart() : null; |
|
78 | - self::$_instance = $saved_cart instanceof EE_Cart ? $saved_cart : new self($grand_total, $session); |
|
79 | - unset($saved_cart); |
|
80 | - } |
|
81 | - // verify that cart is ok and grand total line item exists |
|
82 | - if ( ! self::$_instance instanceof EE_Cart || ! self::$_instance->_grand_total instanceof EE_Line_Item) { |
|
83 | - self::$_instance = new self($grand_total, $session); |
|
84 | - } |
|
85 | - self::$_instance->get_grand_total(); |
|
86 | - // once everything is all said and done, save the cart to the EE_Session |
|
87 | - add_action('shutdown', array(self::$_instance, 'save_cart'), 90); |
|
88 | - return self::$_instance; |
|
89 | - } |
|
90 | - |
|
91 | - |
|
92 | - |
|
93 | - /** |
|
94 | - * private constructor to prevent direct creation |
|
95 | - * |
|
96 | - * @Constructor |
|
97 | - * @access private |
|
98 | - * @param EE_Line_Item $grand_total |
|
99 | - * @param EE_Session $session |
|
100 | - */ |
|
101 | - private function __construct(EE_Line_Item $grand_total = null, EE_Session $session = null) |
|
102 | - { |
|
103 | - do_action('AHEE_log', __FILE__, __FUNCTION__, ''); |
|
104 | - $this->set_session($session); |
|
105 | - if ($grand_total instanceof EE_Line_Item && $grand_total->is_total()) { |
|
106 | - $this->set_grand_total_line_item($grand_total); |
|
107 | - } |
|
108 | - } |
|
109 | - |
|
110 | - |
|
111 | - |
|
112 | - /** |
|
113 | - * Resets the cart completely (whereas empty_cart |
|
114 | - * |
|
115 | - * @param EE_Line_Item $grand_total |
|
116 | - * @param EE_Session $session |
|
117 | - * @return EE_Cart |
|
118 | - * @throws \EE_Error |
|
119 | - */ |
|
120 | - public static function reset(EE_Line_Item $grand_total = null, EE_Session $session = null) |
|
121 | - { |
|
122 | - remove_action('shutdown', array(self::$_instance, 'save_cart'), 90); |
|
123 | - if ($session instanceof EE_Session) { |
|
124 | - $session->reset_cart(); |
|
125 | - } |
|
126 | - self::$_instance = null; |
|
127 | - return self::instance($grand_total, $session); |
|
128 | - } |
|
129 | - |
|
130 | - |
|
131 | - |
|
132 | - /** |
|
133 | - * @return \EE_Session |
|
134 | - */ |
|
135 | - public function session() |
|
136 | - { |
|
137 | - if ( ! $this->_session instanceof EE_Session) { |
|
138 | - $this->set_session(); |
|
139 | - } |
|
140 | - return $this->_session; |
|
141 | - } |
|
142 | - |
|
143 | - |
|
144 | - |
|
145 | - /** |
|
146 | - * @param EE_Session $session |
|
147 | - */ |
|
148 | - public function set_session(EE_Session $session = null) |
|
149 | - { |
|
150 | - $this->_session = $session instanceof EE_Session ? $session : EE_Registry::instance()->load_core('Session'); |
|
151 | - } |
|
152 | - |
|
153 | - |
|
154 | - |
|
155 | - /** |
|
156 | - * Sets the cart to match the line item. Especially handy for loading an old cart where you |
|
157 | - * know the grand total line item on it |
|
158 | - * |
|
159 | - * @param EE_Line_Item $line_item |
|
160 | - */ |
|
161 | - public function set_grand_total_line_item(EE_Line_Item $line_item) |
|
162 | - { |
|
163 | - $this->_grand_total = $line_item; |
|
164 | - } |
|
165 | - |
|
166 | - |
|
167 | - |
|
168 | - /** |
|
169 | - * get_cart_from_reg_url_link |
|
170 | - * |
|
171 | - * @access public |
|
172 | - * @param EE_Transaction $transaction |
|
173 | - * @param EE_Session $session |
|
174 | - * @return \EE_Cart |
|
175 | - * @throws \EE_Error |
|
176 | - */ |
|
177 | - public static function get_cart_from_txn(EE_Transaction $transaction, EE_Session $session = null) |
|
178 | - { |
|
179 | - $grand_total = $transaction->total_line_item(); |
|
180 | - $grand_total->get_items(); |
|
181 | - $grand_total->tax_descendants(); |
|
182 | - return EE_Cart::instance($grand_total, $session); |
|
183 | - } |
|
184 | - |
|
185 | - |
|
186 | - |
|
187 | - /** |
|
188 | - * Creates the total line item, and ensures it has its 'tickets' and 'taxes' sub-items |
|
189 | - * |
|
190 | - * @return EE_Line_Item |
|
191 | - * @throws \EE_Error |
|
192 | - */ |
|
193 | - private function _create_grand_total() |
|
194 | - { |
|
195 | - $this->_grand_total = EEH_Line_Item::create_total_line_item(); |
|
196 | - return $this->_grand_total; |
|
197 | - } |
|
198 | - |
|
199 | - |
|
200 | - |
|
201 | - /** |
|
202 | - * Gets all the line items of object type Ticket |
|
203 | - * |
|
204 | - * @access public |
|
205 | - * @return \EE_Line_Item[] |
|
206 | - */ |
|
207 | - public function get_tickets() |
|
208 | - { |
|
209 | - if ($this->_grand_total === null ) { |
|
210 | - return array(); |
|
211 | - } |
|
212 | - return EEH_Line_Item::get_ticket_line_items($this->_grand_total); |
|
213 | - } |
|
214 | - |
|
215 | - |
|
216 | - |
|
217 | - /** |
|
218 | - * returns the total quantity of tickets in the cart |
|
219 | - * |
|
220 | - * @access public |
|
221 | - * @return int |
|
222 | - * @throws \EE_Error |
|
223 | - */ |
|
224 | - public function all_ticket_quantity_count() |
|
225 | - { |
|
226 | - $tickets = $this->get_tickets(); |
|
227 | - if (empty($tickets)) { |
|
228 | - return 0; |
|
229 | - } |
|
230 | - $count = 0; |
|
231 | - foreach ($tickets as $ticket) { |
|
232 | - $count += $ticket->get('LIN_quantity'); |
|
233 | - } |
|
234 | - return $count; |
|
235 | - } |
|
236 | - |
|
237 | - |
|
238 | - |
|
239 | - /** |
|
240 | - * Gets all the tax line items |
|
241 | - * |
|
242 | - * @return \EE_Line_Item[] |
|
243 | - * @throws \EE_Error |
|
244 | - */ |
|
245 | - public function get_taxes() |
|
246 | - { |
|
247 | - return EEH_Line_Item::get_taxes_subtotal($this->_grand_total)->children(); |
|
248 | - } |
|
249 | - |
|
250 | - |
|
251 | - |
|
252 | - /** |
|
253 | - * Gets the total line item (which is a parent of all other line items) on this cart |
|
254 | - * |
|
255 | - * @return EE_Line_Item |
|
256 | - * @throws \EE_Error |
|
257 | - */ |
|
258 | - public function get_grand_total() |
|
259 | - { |
|
260 | - return $this->_grand_total instanceof EE_Line_Item ? $this->_grand_total : $this->_create_grand_total(); |
|
261 | - } |
|
262 | - |
|
263 | - |
|
264 | - |
|
265 | - /** |
|
266 | - * @process items for adding to cart |
|
267 | - * @access public |
|
268 | - * @param EE_Ticket $ticket |
|
269 | - * @param int $qty |
|
270 | - * @return TRUE on success, FALSE on fail |
|
271 | - * @throws \EE_Error |
|
272 | - */ |
|
273 | - public function add_ticket_to_cart(EE_Ticket $ticket, $qty = 1) |
|
274 | - { |
|
275 | - EEH_Line_Item::add_ticket_purchase($this->get_grand_total(), $ticket, $qty); |
|
276 | - return $this->save_cart() ? true : false; |
|
277 | - } |
|
278 | - |
|
279 | - |
|
280 | - |
|
281 | - /** |
|
282 | - * get_cart_total_before_tax |
|
283 | - * |
|
284 | - * @access public |
|
285 | - * @return float |
|
286 | - * @throws \EE_Error |
|
287 | - */ |
|
288 | - public function get_cart_total_before_tax() |
|
289 | - { |
|
290 | - return $this->get_grand_total()->recalculate_pre_tax_total(); |
|
291 | - } |
|
292 | - |
|
293 | - |
|
294 | - |
|
295 | - /** |
|
296 | - * gets the total amount of tax paid for items in this cart |
|
297 | - * |
|
298 | - * @access public |
|
299 | - * @return float |
|
300 | - * @throws \EE_Error |
|
301 | - */ |
|
302 | - public function get_applied_taxes() |
|
303 | - { |
|
304 | - return EEH_Line_Item::ensure_taxes_applied($this->_grand_total); |
|
305 | - } |
|
306 | - |
|
307 | - |
|
308 | - |
|
309 | - /** |
|
310 | - * Gets the total amount to be paid for the items in the cart, including taxes and other modifiers |
|
311 | - * |
|
312 | - * @access public |
|
313 | - * @return float |
|
314 | - * @throws \EE_Error |
|
315 | - */ |
|
316 | - public function get_cart_grand_total() |
|
317 | - { |
|
318 | - EEH_Line_Item::ensure_taxes_applied($this->_grand_total); |
|
319 | - return $this->get_grand_total()->total(); |
|
320 | - } |
|
321 | - |
|
322 | - |
|
323 | - |
|
324 | - /** |
|
325 | - * Gets the total amount to be paid for the items in the cart, including taxes and other modifiers |
|
326 | - * |
|
327 | - * @access public |
|
328 | - * @return float |
|
329 | - * @throws \EE_Error |
|
330 | - */ |
|
331 | - public function recalculate_all_cart_totals() |
|
332 | - { |
|
333 | - $pre_tax_total = $this->get_cart_total_before_tax(); |
|
334 | - $taxes_total = EEH_Line_Item::ensure_taxes_applied($this->_grand_total); |
|
335 | - $this->_grand_total->set_total($pre_tax_total + $taxes_total); |
|
336 | - $this->_grand_total->save_this_and_descendants_to_txn(); |
|
337 | - return $this->get_grand_total()->total(); |
|
338 | - } |
|
339 | - |
|
340 | - |
|
341 | - |
|
342 | - /** |
|
343 | - * deletes an item from the cart |
|
344 | - * |
|
345 | - * @access public |
|
346 | - * @param array|bool|string $line_item_codes |
|
347 | - * @return int on success, FALSE on fail |
|
348 | - * @throws \EE_Error |
|
349 | - */ |
|
350 | - public function delete_items($line_item_codes = false) |
|
351 | - { |
|
352 | - do_action('AHEE_log', __FILE__, __FUNCTION__, ''); |
|
353 | - return EEH_Line_Item::delete_items($this->get_grand_total(), $line_item_codes); |
|
354 | - } |
|
355 | - |
|
356 | - |
|
357 | - |
|
358 | - /** |
|
359 | - * @remove ALL items from cart and zero ALL totals |
|
360 | - * @access public |
|
361 | - * @return bool |
|
362 | - * @throws \EE_Error |
|
363 | - */ |
|
364 | - public function empty_cart() |
|
365 | - { |
|
366 | - do_action('AHEE_log', __FILE__, __FUNCTION__, ''); |
|
367 | - $this->_grand_total = $this->_create_grand_total(); |
|
368 | - return $this->save_cart(true); |
|
369 | - } |
|
370 | - |
|
371 | - |
|
372 | - |
|
373 | - /** |
|
374 | - * @remove ALL items from cart and delete total as well |
|
375 | - * @access public |
|
376 | - * @return bool |
|
377 | - * @throws \EE_Error |
|
378 | - */ |
|
379 | - public function delete_cart() |
|
380 | - { |
|
381 | - $deleted = EEH_Line_Item::delete_all_child_items($this->_grand_total); |
|
382 | - if ($deleted) { |
|
383 | - $deleted += $this->_grand_total->delete(); |
|
384 | - $this->_grand_total = null; |
|
385 | - } |
|
386 | - return $deleted; |
|
387 | - } |
|
388 | - |
|
389 | - |
|
390 | - |
|
391 | - /** |
|
392 | - * @save cart to session |
|
393 | - * @access public |
|
394 | - * @param bool $apply_taxes |
|
395 | - * @return TRUE on success, FALSE on fail |
|
396 | - * @throws \EE_Error |
|
397 | - */ |
|
398 | - public function save_cart($apply_taxes = true) |
|
399 | - { |
|
400 | - if ($apply_taxes && $this->_grand_total instanceof EE_Line_Item) { |
|
401 | - EEH_Line_Item::ensure_taxes_applied($this->_grand_total); |
|
402 | - //make sure we don't cache the transaction because it can get stale |
|
403 | - if ($this->_grand_total->get_one_from_cache('Transaction') instanceof EE_Transaction |
|
404 | - && $this->_grand_total->get_one_from_cache('Transaction')->ID() |
|
405 | - ) { |
|
406 | - $this->_grand_total->clear_cache('Transaction', null, true); |
|
407 | - } |
|
408 | - } |
|
409 | - if ($this->session() instanceof EE_Session) { |
|
410 | - return $this->session()->set_cart($this); |
|
411 | - } else { |
|
412 | - return false; |
|
413 | - } |
|
414 | - } |
|
415 | - |
|
416 | - |
|
417 | - |
|
418 | - public function __wakeup() |
|
419 | - { |
|
420 | - if ( ! $this->_grand_total instanceof EE_Line_Item && absint($this->_grand_total) !== 0) { |
|
421 | - // $this->_grand_total is actually just an ID, so use it to get the object from the db |
|
422 | - $this->_grand_total = EEM_Line_Item::instance()->get_one_by_ID($this->_grand_total); |
|
423 | - } |
|
424 | - } |
|
425 | - |
|
426 | - |
|
427 | - |
|
428 | - /** |
|
429 | - * @return array |
|
430 | - */ |
|
431 | - public function __sleep() |
|
432 | - { |
|
433 | - if ($this->_grand_total instanceof EE_Line_Item && $this->_grand_total->ID()) { |
|
434 | - $this->_grand_total = $this->_grand_total->ID(); |
|
435 | - } |
|
436 | - return array('_grand_total'); |
|
437 | - } |
|
26 | + /** |
|
27 | + * instance of the EE_Cart object |
|
28 | + * |
|
29 | + * @access private |
|
30 | + * @var EE_Cart $_instance |
|
31 | + */ |
|
32 | + private static $_instance; |
|
33 | + |
|
34 | + /** |
|
35 | + * instance of the EE_Session object |
|
36 | + * |
|
37 | + * @access protected |
|
38 | + * @var EE_Session $_session |
|
39 | + */ |
|
40 | + protected $_session; |
|
41 | + |
|
42 | + /** |
|
43 | + * The total Line item which comprises all the children line-item subtotals, |
|
44 | + * which in turn each have their line items. |
|
45 | + * Typically, the line item structure will look like: |
|
46 | + * grand total |
|
47 | + * -tickets-sub-total |
|
48 | + * --ticket1 |
|
49 | + * --ticket2 |
|
50 | + * --... |
|
51 | + * -taxes-sub-total |
|
52 | + * --tax1 |
|
53 | + * --tax2 |
|
54 | + * |
|
55 | + * @var EE_Line_Item |
|
56 | + */ |
|
57 | + private $_grand_total; |
|
58 | + |
|
59 | + |
|
60 | + |
|
61 | + /** |
|
62 | + * @singleton method used to instantiate class object |
|
63 | + * @access public |
|
64 | + * @param EE_Line_Item $grand_total |
|
65 | + * @param EE_Session $session |
|
66 | + * @return \EE_Cart |
|
67 | + * @throws \EE_Error |
|
68 | + */ |
|
69 | + public static function instance(EE_Line_Item $grand_total = null, EE_Session $session = null) |
|
70 | + { |
|
71 | + if ( ! empty($grand_total)) { |
|
72 | + self::$_instance = new self($grand_total, $session); |
|
73 | + } |
|
74 | + // or maybe retrieve an existing one ? |
|
75 | + if ( ! self::$_instance instanceof EE_Cart) { |
|
76 | + // try getting the cart out of the session |
|
77 | + $saved_cart = $session instanceof EE_Session ? $session->cart() : null; |
|
78 | + self::$_instance = $saved_cart instanceof EE_Cart ? $saved_cart : new self($grand_total, $session); |
|
79 | + unset($saved_cart); |
|
80 | + } |
|
81 | + // verify that cart is ok and grand total line item exists |
|
82 | + if ( ! self::$_instance instanceof EE_Cart || ! self::$_instance->_grand_total instanceof EE_Line_Item) { |
|
83 | + self::$_instance = new self($grand_total, $session); |
|
84 | + } |
|
85 | + self::$_instance->get_grand_total(); |
|
86 | + // once everything is all said and done, save the cart to the EE_Session |
|
87 | + add_action('shutdown', array(self::$_instance, 'save_cart'), 90); |
|
88 | + return self::$_instance; |
|
89 | + } |
|
90 | + |
|
91 | + |
|
92 | + |
|
93 | + /** |
|
94 | + * private constructor to prevent direct creation |
|
95 | + * |
|
96 | + * @Constructor |
|
97 | + * @access private |
|
98 | + * @param EE_Line_Item $grand_total |
|
99 | + * @param EE_Session $session |
|
100 | + */ |
|
101 | + private function __construct(EE_Line_Item $grand_total = null, EE_Session $session = null) |
|
102 | + { |
|
103 | + do_action('AHEE_log', __FILE__, __FUNCTION__, ''); |
|
104 | + $this->set_session($session); |
|
105 | + if ($grand_total instanceof EE_Line_Item && $grand_total->is_total()) { |
|
106 | + $this->set_grand_total_line_item($grand_total); |
|
107 | + } |
|
108 | + } |
|
109 | + |
|
110 | + |
|
111 | + |
|
112 | + /** |
|
113 | + * Resets the cart completely (whereas empty_cart |
|
114 | + * |
|
115 | + * @param EE_Line_Item $grand_total |
|
116 | + * @param EE_Session $session |
|
117 | + * @return EE_Cart |
|
118 | + * @throws \EE_Error |
|
119 | + */ |
|
120 | + public static function reset(EE_Line_Item $grand_total = null, EE_Session $session = null) |
|
121 | + { |
|
122 | + remove_action('shutdown', array(self::$_instance, 'save_cart'), 90); |
|
123 | + if ($session instanceof EE_Session) { |
|
124 | + $session->reset_cart(); |
|
125 | + } |
|
126 | + self::$_instance = null; |
|
127 | + return self::instance($grand_total, $session); |
|
128 | + } |
|
129 | + |
|
130 | + |
|
131 | + |
|
132 | + /** |
|
133 | + * @return \EE_Session |
|
134 | + */ |
|
135 | + public function session() |
|
136 | + { |
|
137 | + if ( ! $this->_session instanceof EE_Session) { |
|
138 | + $this->set_session(); |
|
139 | + } |
|
140 | + return $this->_session; |
|
141 | + } |
|
142 | + |
|
143 | + |
|
144 | + |
|
145 | + /** |
|
146 | + * @param EE_Session $session |
|
147 | + */ |
|
148 | + public function set_session(EE_Session $session = null) |
|
149 | + { |
|
150 | + $this->_session = $session instanceof EE_Session ? $session : EE_Registry::instance()->load_core('Session'); |
|
151 | + } |
|
152 | + |
|
153 | + |
|
154 | + |
|
155 | + /** |
|
156 | + * Sets the cart to match the line item. Especially handy for loading an old cart where you |
|
157 | + * know the grand total line item on it |
|
158 | + * |
|
159 | + * @param EE_Line_Item $line_item |
|
160 | + */ |
|
161 | + public function set_grand_total_line_item(EE_Line_Item $line_item) |
|
162 | + { |
|
163 | + $this->_grand_total = $line_item; |
|
164 | + } |
|
165 | + |
|
166 | + |
|
167 | + |
|
168 | + /** |
|
169 | + * get_cart_from_reg_url_link |
|
170 | + * |
|
171 | + * @access public |
|
172 | + * @param EE_Transaction $transaction |
|
173 | + * @param EE_Session $session |
|
174 | + * @return \EE_Cart |
|
175 | + * @throws \EE_Error |
|
176 | + */ |
|
177 | + public static function get_cart_from_txn(EE_Transaction $transaction, EE_Session $session = null) |
|
178 | + { |
|
179 | + $grand_total = $transaction->total_line_item(); |
|
180 | + $grand_total->get_items(); |
|
181 | + $grand_total->tax_descendants(); |
|
182 | + return EE_Cart::instance($grand_total, $session); |
|
183 | + } |
|
184 | + |
|
185 | + |
|
186 | + |
|
187 | + /** |
|
188 | + * Creates the total line item, and ensures it has its 'tickets' and 'taxes' sub-items |
|
189 | + * |
|
190 | + * @return EE_Line_Item |
|
191 | + * @throws \EE_Error |
|
192 | + */ |
|
193 | + private function _create_grand_total() |
|
194 | + { |
|
195 | + $this->_grand_total = EEH_Line_Item::create_total_line_item(); |
|
196 | + return $this->_grand_total; |
|
197 | + } |
|
198 | + |
|
199 | + |
|
200 | + |
|
201 | + /** |
|
202 | + * Gets all the line items of object type Ticket |
|
203 | + * |
|
204 | + * @access public |
|
205 | + * @return \EE_Line_Item[] |
|
206 | + */ |
|
207 | + public function get_tickets() |
|
208 | + { |
|
209 | + if ($this->_grand_total === null ) { |
|
210 | + return array(); |
|
211 | + } |
|
212 | + return EEH_Line_Item::get_ticket_line_items($this->_grand_total); |
|
213 | + } |
|
214 | + |
|
215 | + |
|
216 | + |
|
217 | + /** |
|
218 | + * returns the total quantity of tickets in the cart |
|
219 | + * |
|
220 | + * @access public |
|
221 | + * @return int |
|
222 | + * @throws \EE_Error |
|
223 | + */ |
|
224 | + public function all_ticket_quantity_count() |
|
225 | + { |
|
226 | + $tickets = $this->get_tickets(); |
|
227 | + if (empty($tickets)) { |
|
228 | + return 0; |
|
229 | + } |
|
230 | + $count = 0; |
|
231 | + foreach ($tickets as $ticket) { |
|
232 | + $count += $ticket->get('LIN_quantity'); |
|
233 | + } |
|
234 | + return $count; |
|
235 | + } |
|
236 | + |
|
237 | + |
|
238 | + |
|
239 | + /** |
|
240 | + * Gets all the tax line items |
|
241 | + * |
|
242 | + * @return \EE_Line_Item[] |
|
243 | + * @throws \EE_Error |
|
244 | + */ |
|
245 | + public function get_taxes() |
|
246 | + { |
|
247 | + return EEH_Line_Item::get_taxes_subtotal($this->_grand_total)->children(); |
|
248 | + } |
|
249 | + |
|
250 | + |
|
251 | + |
|
252 | + /** |
|
253 | + * Gets the total line item (which is a parent of all other line items) on this cart |
|
254 | + * |
|
255 | + * @return EE_Line_Item |
|
256 | + * @throws \EE_Error |
|
257 | + */ |
|
258 | + public function get_grand_total() |
|
259 | + { |
|
260 | + return $this->_grand_total instanceof EE_Line_Item ? $this->_grand_total : $this->_create_grand_total(); |
|
261 | + } |
|
262 | + |
|
263 | + |
|
264 | + |
|
265 | + /** |
|
266 | + * @process items for adding to cart |
|
267 | + * @access public |
|
268 | + * @param EE_Ticket $ticket |
|
269 | + * @param int $qty |
|
270 | + * @return TRUE on success, FALSE on fail |
|
271 | + * @throws \EE_Error |
|
272 | + */ |
|
273 | + public function add_ticket_to_cart(EE_Ticket $ticket, $qty = 1) |
|
274 | + { |
|
275 | + EEH_Line_Item::add_ticket_purchase($this->get_grand_total(), $ticket, $qty); |
|
276 | + return $this->save_cart() ? true : false; |
|
277 | + } |
|
278 | + |
|
279 | + |
|
280 | + |
|
281 | + /** |
|
282 | + * get_cart_total_before_tax |
|
283 | + * |
|
284 | + * @access public |
|
285 | + * @return float |
|
286 | + * @throws \EE_Error |
|
287 | + */ |
|
288 | + public function get_cart_total_before_tax() |
|
289 | + { |
|
290 | + return $this->get_grand_total()->recalculate_pre_tax_total(); |
|
291 | + } |
|
292 | + |
|
293 | + |
|
294 | + |
|
295 | + /** |
|
296 | + * gets the total amount of tax paid for items in this cart |
|
297 | + * |
|
298 | + * @access public |
|
299 | + * @return float |
|
300 | + * @throws \EE_Error |
|
301 | + */ |
|
302 | + public function get_applied_taxes() |
|
303 | + { |
|
304 | + return EEH_Line_Item::ensure_taxes_applied($this->_grand_total); |
|
305 | + } |
|
306 | + |
|
307 | + |
|
308 | + |
|
309 | + /** |
|
310 | + * Gets the total amount to be paid for the items in the cart, including taxes and other modifiers |
|
311 | + * |
|
312 | + * @access public |
|
313 | + * @return float |
|
314 | + * @throws \EE_Error |
|
315 | + */ |
|
316 | + public function get_cart_grand_total() |
|
317 | + { |
|
318 | + EEH_Line_Item::ensure_taxes_applied($this->_grand_total); |
|
319 | + return $this->get_grand_total()->total(); |
|
320 | + } |
|
321 | + |
|
322 | + |
|
323 | + |
|
324 | + /** |
|
325 | + * Gets the total amount to be paid for the items in the cart, including taxes and other modifiers |
|
326 | + * |
|
327 | + * @access public |
|
328 | + * @return float |
|
329 | + * @throws \EE_Error |
|
330 | + */ |
|
331 | + public function recalculate_all_cart_totals() |
|
332 | + { |
|
333 | + $pre_tax_total = $this->get_cart_total_before_tax(); |
|
334 | + $taxes_total = EEH_Line_Item::ensure_taxes_applied($this->_grand_total); |
|
335 | + $this->_grand_total->set_total($pre_tax_total + $taxes_total); |
|
336 | + $this->_grand_total->save_this_and_descendants_to_txn(); |
|
337 | + return $this->get_grand_total()->total(); |
|
338 | + } |
|
339 | + |
|
340 | + |
|
341 | + |
|
342 | + /** |
|
343 | + * deletes an item from the cart |
|
344 | + * |
|
345 | + * @access public |
|
346 | + * @param array|bool|string $line_item_codes |
|
347 | + * @return int on success, FALSE on fail |
|
348 | + * @throws \EE_Error |
|
349 | + */ |
|
350 | + public function delete_items($line_item_codes = false) |
|
351 | + { |
|
352 | + do_action('AHEE_log', __FILE__, __FUNCTION__, ''); |
|
353 | + return EEH_Line_Item::delete_items($this->get_grand_total(), $line_item_codes); |
|
354 | + } |
|
355 | + |
|
356 | + |
|
357 | + |
|
358 | + /** |
|
359 | + * @remove ALL items from cart and zero ALL totals |
|
360 | + * @access public |
|
361 | + * @return bool |
|
362 | + * @throws \EE_Error |
|
363 | + */ |
|
364 | + public function empty_cart() |
|
365 | + { |
|
366 | + do_action('AHEE_log', __FILE__, __FUNCTION__, ''); |
|
367 | + $this->_grand_total = $this->_create_grand_total(); |
|
368 | + return $this->save_cart(true); |
|
369 | + } |
|
370 | + |
|
371 | + |
|
372 | + |
|
373 | + /** |
|
374 | + * @remove ALL items from cart and delete total as well |
|
375 | + * @access public |
|
376 | + * @return bool |
|
377 | + * @throws \EE_Error |
|
378 | + */ |
|
379 | + public function delete_cart() |
|
380 | + { |
|
381 | + $deleted = EEH_Line_Item::delete_all_child_items($this->_grand_total); |
|
382 | + if ($deleted) { |
|
383 | + $deleted += $this->_grand_total->delete(); |
|
384 | + $this->_grand_total = null; |
|
385 | + } |
|
386 | + return $deleted; |
|
387 | + } |
|
388 | + |
|
389 | + |
|
390 | + |
|
391 | + /** |
|
392 | + * @save cart to session |
|
393 | + * @access public |
|
394 | + * @param bool $apply_taxes |
|
395 | + * @return TRUE on success, FALSE on fail |
|
396 | + * @throws \EE_Error |
|
397 | + */ |
|
398 | + public function save_cart($apply_taxes = true) |
|
399 | + { |
|
400 | + if ($apply_taxes && $this->_grand_total instanceof EE_Line_Item) { |
|
401 | + EEH_Line_Item::ensure_taxes_applied($this->_grand_total); |
|
402 | + //make sure we don't cache the transaction because it can get stale |
|
403 | + if ($this->_grand_total->get_one_from_cache('Transaction') instanceof EE_Transaction |
|
404 | + && $this->_grand_total->get_one_from_cache('Transaction')->ID() |
|
405 | + ) { |
|
406 | + $this->_grand_total->clear_cache('Transaction', null, true); |
|
407 | + } |
|
408 | + } |
|
409 | + if ($this->session() instanceof EE_Session) { |
|
410 | + return $this->session()->set_cart($this); |
|
411 | + } else { |
|
412 | + return false; |
|
413 | + } |
|
414 | + } |
|
415 | + |
|
416 | + |
|
417 | + |
|
418 | + public function __wakeup() |
|
419 | + { |
|
420 | + if ( ! $this->_grand_total instanceof EE_Line_Item && absint($this->_grand_total) !== 0) { |
|
421 | + // $this->_grand_total is actually just an ID, so use it to get the object from the db |
|
422 | + $this->_grand_total = EEM_Line_Item::instance()->get_one_by_ID($this->_grand_total); |
|
423 | + } |
|
424 | + } |
|
425 | + |
|
426 | + |
|
427 | + |
|
428 | + /** |
|
429 | + * @return array |
|
430 | + */ |
|
431 | + public function __sleep() |
|
432 | + { |
|
433 | + if ($this->_grand_total instanceof EE_Line_Item && $this->_grand_total->ID()) { |
|
434 | + $this->_grand_total = $this->_grand_total->ID(); |
|
435 | + } |
|
436 | + return array('_grand_total'); |
|
437 | + } |
|
438 | 438 | |
439 | 439 | |
440 | 440 | } |
@@ -1,7 +1,7 @@ discard block |
||
1 | 1 | <?php use EventEspresso\core\interfaces\ResettableInterface; |
2 | 2 | |
3 | 3 | if ( ! defined('EVENT_ESPRESSO_VERSION')) { |
4 | - exit('No direct script access allowed'); |
|
4 | + exit('No direct script access allowed'); |
|
5 | 5 | } |
6 | 6 | |
7 | 7 | |
@@ -17,748 +17,748 @@ discard block |
||
17 | 17 | class EE_Payment_Processor extends EE_Processor_Base implements ResettableInterface |
18 | 18 | { |
19 | 19 | |
20 | - /** |
|
21 | - * @var EE_Payment_Processor $_instance |
|
22 | - * @access private |
|
23 | - */ |
|
24 | - private static $_instance; |
|
25 | - |
|
26 | - |
|
27 | - |
|
28 | - /** |
|
29 | - * @singleton method used to instantiate class object |
|
30 | - * @access public |
|
31 | - * @return EE_Payment_Processor instance |
|
32 | - */ |
|
33 | - public static function instance() |
|
34 | - { |
|
35 | - // check if class object is instantiated |
|
36 | - if ( ! self::$_instance instanceof EE_Payment_Processor) { |
|
37 | - self::$_instance = new self(); |
|
38 | - } |
|
39 | - return self::$_instance; |
|
40 | - } |
|
41 | - |
|
42 | - |
|
43 | - |
|
44 | - /** |
|
45 | - * @return EE_Payment_Processor |
|
46 | - */ |
|
47 | - public static function reset() |
|
48 | - { |
|
49 | - self::$_instance = null; |
|
50 | - return self::instance(); |
|
51 | - } |
|
52 | - |
|
53 | - |
|
54 | - |
|
55 | - /** |
|
56 | - *private constructor to prevent direct creation |
|
57 | - * |
|
58 | - * @Constructor |
|
59 | - * @access private |
|
60 | - */ |
|
61 | - private function __construct() |
|
62 | - { |
|
63 | - do_action('AHEE__EE_Payment_Processor__construct'); |
|
64 | - add_action('http_api_curl', array($this, '_curl_requests_to_paypal_use_tls'), 10, 3); |
|
65 | - } |
|
66 | - |
|
67 | - |
|
68 | - |
|
69 | - /** |
|
70 | - * Using the selected gateway, processes the payment for that transaction, and updates the transaction |
|
71 | - * appropriately. Saves the payment that is generated |
|
72 | - * |
|
73 | - * @param EE_Payment_Method $payment_method |
|
74 | - * @param EE_Transaction $transaction |
|
75 | - * @param float $amount if only part of the transaction is to be paid for, how much. |
|
76 | - * Leave null if payment is for the full amount owing |
|
77 | - * @param EE_Billing_Info_Form $billing_form (or probably null, if it's an offline or offsite payment method). |
|
78 | - * Receive_form_submission() should have |
|
79 | - * already been called on the billing form |
|
80 | - * (ie, its inputs should have their normalized values set). |
|
81 | - * @param string $return_url string used mostly by offsite gateways to specify |
|
82 | - * where to go AFTER the offsite gateway |
|
83 | - * @param string $method like 'CART', indicates who the client who called this was |
|
84 | - * @param bool $by_admin TRUE if payment is being attempted from the admin |
|
85 | - * @param boolean $update_txn whether or not to call |
|
86 | - * EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() |
|
87 | - * @param string $cancel_url URL to return to if off-site payments are cancelled |
|
88 | - * @return \EE_Payment |
|
89 | - * @throws \EE_Error |
|
90 | - */ |
|
91 | - public function process_payment( |
|
92 | - EE_Payment_Method $payment_method, |
|
93 | - EE_Transaction $transaction, |
|
94 | - $amount = null, |
|
95 | - $billing_form = null, |
|
96 | - $return_url = null, |
|
97 | - $method = 'CART', |
|
98 | - $by_admin = false, |
|
99 | - $update_txn = true, |
|
100 | - $cancel_url = '' |
|
101 | - ) { |
|
102 | - if ((float)$amount < 0) { |
|
103 | - throw new EE_Error( |
|
104 | - sprintf( |
|
105 | - __( |
|
106 | - 'Attempting to make a payment for a negative amount of %1$d for transaction %2$d. That should be a refund', |
|
107 | - 'event_espresso' |
|
108 | - ), |
|
109 | - $amount, |
|
110 | - $transaction->ID() |
|
111 | - ) |
|
112 | - ); |
|
113 | - } |
|
114 | - // verify payment method |
|
115 | - $payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method, true); |
|
116 | - // verify transaction |
|
117 | - EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
118 | - $transaction->set_payment_method_ID($payment_method->ID()); |
|
119 | - // verify payment method type |
|
120 | - if ($payment_method->type_obj() instanceof EE_PMT_Base) { |
|
121 | - $payment = $payment_method->type_obj()->process_payment( |
|
122 | - $transaction, |
|
123 | - min($amount, $transaction->remaining()),//make sure we don't overcharge |
|
124 | - $billing_form, |
|
125 | - $return_url, |
|
126 | - add_query_arg(array('ee_cancel_payment' => true), $cancel_url), |
|
127 | - $method, |
|
128 | - $by_admin |
|
129 | - ); |
|
130 | - // check if payment method uses an off-site gateway |
|
131 | - if ($payment_method->type_obj()->payment_occurs() !== EE_PMT_Base::offsite) { |
|
132 | - // don't process payments for off-site gateways yet because no payment has occurred yet |
|
133 | - $this->update_txn_based_on_payment($transaction, $payment, $update_txn); |
|
134 | - } |
|
135 | - return $payment; |
|
136 | - } else { |
|
137 | - EE_Error::add_error( |
|
138 | - sprintf( |
|
139 | - __('A valid payment method could not be determined due to a technical issue.%sPlease try again or contact %s for assistance.', 'event_espresso'), |
|
140 | - '<br/>', |
|
141 | - EE_Registry::instance()->CFG->organization->get_pretty('email') |
|
142 | - ), __FILE__, __FUNCTION__, __LINE__ |
|
143 | - ); |
|
144 | - return null; |
|
145 | - } |
|
146 | - } |
|
147 | - |
|
148 | - |
|
149 | - |
|
150 | - /** |
|
151 | - * @param EE_Transaction|int $transaction |
|
152 | - * @param EE_Payment_Method $payment_method |
|
153 | - * @throws EE_Error |
|
154 | - * @return string |
|
155 | - */ |
|
156 | - public function get_ipn_url_for_payment_method($transaction, $payment_method) |
|
157 | - { |
|
158 | - /** @type \EE_Transaction $transaction */ |
|
159 | - $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
160 | - $primary_reg = $transaction->primary_registration(); |
|
161 | - if ( ! $primary_reg instanceof EE_Registration) { |
|
162 | - throw new EE_Error( |
|
163 | - sprintf( |
|
164 | - __( |
|
165 | - "Cannot get IPN URL for transaction with ID %d because it has no primary registration", |
|
166 | - "event_espresso" |
|
167 | - ), |
|
168 | - $transaction->ID() |
|
169 | - ) |
|
170 | - ); |
|
171 | - } |
|
172 | - $payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method, true); |
|
173 | - $url = add_query_arg( |
|
174 | - array( |
|
175 | - 'e_reg_url_link' => $primary_reg->reg_url_link(), |
|
176 | - 'ee_payment_method' => $payment_method->slug(), |
|
177 | - ), |
|
178 | - EE_Registry::instance()->CFG->core->txn_page_url() |
|
179 | - ); |
|
180 | - return $url; |
|
181 | - } |
|
182 | - |
|
183 | - |
|
184 | - |
|
185 | - /** |
|
186 | - * Process the IPN. Firstly, we'll hope we put the standard args into the IPN URL so |
|
187 | - * we can easily find what registration the IPN is for and what payment method. |
|
188 | - * However, if not, we'll give all payment methods a chance to claim it and process it. |
|
189 | - * If a payment is found for the IPN info, it is saved. |
|
190 | - * |
|
191 | - * @param array $_req_data eg $_REQUEST |
|
192 | - * @param EE_Transaction|int $transaction optional (or a transactions id) |
|
193 | - * @param EE_Payment_Method $payment_method (or a slug or id of one) |
|
194 | - * @param boolean $update_txn whether or not to call |
|
195 | - * EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() |
|
196 | - * @param bool $separate_IPN_request whether the IPN uses a separate request ( true like PayPal ) |
|
197 | - * or is processed manually ( false like Mijireh ) |
|
198 | - * @throws EE_Error |
|
199 | - * @throws Exception |
|
200 | - * @return EE_Payment |
|
201 | - */ |
|
202 | - public function process_ipn( |
|
203 | - $_req_data, |
|
204 | - $transaction = null, |
|
205 | - $payment_method = null, |
|
206 | - $update_txn = true, |
|
207 | - $separate_IPN_request = true |
|
208 | - ) { |
|
209 | - EE_Registry::instance()->load_model('Change_Log'); |
|
210 | - $_req_data = $this->_remove_unusable_characters_from_array((array)$_req_data); |
|
211 | - EE_Processor_Base::set_IPN($separate_IPN_request); |
|
212 | - $obj_for_log = null; |
|
213 | - if ($transaction instanceof EE_Transaction) { |
|
214 | - $obj_for_log = $transaction; |
|
215 | - if ($payment_method instanceof EE_Payment_Method) { |
|
216 | - $obj_for_log = EEM_Payment::instance()->get_one( |
|
217 | - array( |
|
218 | - array('TXN_ID' => $transaction->ID(), 'PMD_ID' => $payment_method->ID()), |
|
219 | - 'order_by' => array('PAY_timestamp' => 'desc'), |
|
220 | - ) |
|
221 | - ); |
|
222 | - } |
|
223 | - } else if ($payment_method instanceof EE_Payment) { |
|
224 | - $obj_for_log = $payment_method; |
|
225 | - } |
|
226 | - $log = EEM_Change_Log::instance()->log( |
|
227 | - EEM_Change_Log::type_gateway, |
|
228 | - array('IPN data received' => $_req_data), |
|
229 | - $obj_for_log |
|
230 | - ); |
|
231 | - try { |
|
232 | - /** |
|
233 | - * @var EE_Payment $payment |
|
234 | - */ |
|
235 | - $payment = null; |
|
236 | - if ($transaction && $payment_method) { |
|
237 | - /** @type EE_Transaction $transaction */ |
|
238 | - $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
239 | - /** @type EE_Payment_Method $payment_method */ |
|
240 | - $payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method); |
|
241 | - if ($payment_method->type_obj() instanceof EE_PMT_Base) { |
|
242 | - try { |
|
243 | - $payment = $payment_method->type_obj()->handle_ipn($_req_data, $transaction); |
|
244 | - $log->set_object($payment); |
|
245 | - } catch (EventEspresso\core\exceptions\IpnException $e) { |
|
246 | - EEM_Change_Log::instance()->log( |
|
247 | - EEM_Change_Log::type_gateway, |
|
248 | - array( |
|
249 | - 'message' => 'IPN Exception: ' . $e->getMessage(), |
|
250 | - 'current_url' => EEH_URL::current_url(), |
|
251 | - 'payment' => $e->getPaymentProperties(), |
|
252 | - 'IPN_data' => $e->getIpnData(), |
|
253 | - ), |
|
254 | - $obj_for_log |
|
255 | - ); |
|
256 | - return $e->getPayment(); |
|
257 | - } |
|
258 | - } else { |
|
259 | - // not a payment |
|
260 | - EE_Error::add_error( |
|
261 | - sprintf( |
|
262 | - __('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'), |
|
263 | - '<br/>', |
|
264 | - EE_Registry::instance()->CFG->organization->get_pretty('email') |
|
265 | - ), |
|
266 | - __FILE__, __FUNCTION__, __LINE__ |
|
267 | - ); |
|
268 | - } |
|
269 | - } else { |
|
270 | - //that's actually pretty ok. The IPN just wasn't able |
|
271 | - //to identify which transaction or payment method this was for |
|
272 | - // give all active payment methods a chance to claim it |
|
273 | - $active_payment_methods = EEM_Payment_Method::instance()->get_all_active(); |
|
274 | - foreach ($active_payment_methods as $active_payment_method) { |
|
275 | - try { |
|
276 | - $payment = $active_payment_method->type_obj()->handle_unclaimed_ipn($_req_data); |
|
277 | - $payment_method = $active_payment_method; |
|
278 | - EEM_Change_Log::instance()->log( |
|
279 | - EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $payment |
|
280 | - ); |
|
281 | - break; |
|
282 | - } catch (EventEspresso\core\exceptions\IpnException $e) { |
|
283 | - EEM_Change_Log::instance()->log( |
|
284 | - EEM_Change_Log::type_gateway, |
|
285 | - array( |
|
286 | - 'message' => 'IPN Exception: ' . $e->getMessage(), |
|
287 | - 'current_url' => EEH_URL::current_url(), |
|
288 | - 'payment' => $e->getPaymentProperties(), |
|
289 | - 'IPN_data' => $e->getIpnData(), |
|
290 | - ), |
|
291 | - $obj_for_log |
|
292 | - ); |
|
293 | - return $e->getPayment(); |
|
294 | - } catch (EE_Error $e) { |
|
295 | - //that's fine- it apparently couldn't handle the IPN |
|
296 | - } |
|
297 | - } |
|
298 | - } |
|
299 | - // EEM_Payment_Log::instance()->log("got to 7",$transaction,$payment_method); |
|
300 | - if ($payment instanceof EE_Payment) { |
|
301 | - $payment->save(); |
|
302 | - // update the TXN |
|
303 | - $this->update_txn_based_on_payment($transaction, $payment, $update_txn, $separate_IPN_request); |
|
304 | - } else { |
|
305 | - //we couldn't find the payment for this IPN... let's try and log at least SOMETHING |
|
306 | - if ($payment_method) { |
|
307 | - EEM_Change_Log::instance()->log(EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $payment_method); |
|
308 | - } elseif ($transaction) { |
|
309 | - EEM_Change_Log::instance()->log(EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $transaction); |
|
310 | - } |
|
311 | - } |
|
312 | - return $payment; |
|
313 | - } catch (EE_Error $e) { |
|
314 | - do_action( |
|
315 | - 'AHEE__log', __FILE__, __FUNCTION__, sprintf( |
|
316 | - __('Error occurred while receiving IPN. Transaction: %1$s, req data: %2$s. The error was "%3$s"', 'event_espresso'), |
|
317 | - print_r($transaction, true), |
|
318 | - print_r($_req_data, true), |
|
319 | - $e->getMessage() |
|
320 | - ) |
|
321 | - ); |
|
322 | - throw $e; |
|
323 | - } |
|
324 | - } |
|
325 | - |
|
326 | - |
|
327 | - |
|
328 | - /** |
|
329 | - * Removes any non-printable illegal characters from the input, |
|
330 | - * which might cause a raucous when trying to insert into the database |
|
331 | - * |
|
332 | - * @param array $request_data |
|
333 | - * @return array |
|
334 | - */ |
|
335 | - protected function _remove_unusable_characters_from_array(array $request_data) |
|
336 | - { |
|
337 | - $return_data = array(); |
|
338 | - foreach ($request_data as $key => $value) { |
|
339 | - $return_data[$this->_remove_unusable_characters($key)] = $this->_remove_unusable_characters($value); |
|
340 | - } |
|
341 | - return $return_data; |
|
342 | - } |
|
343 | - |
|
344 | - |
|
345 | - |
|
346 | - /** |
|
347 | - * Removes any non-printable illegal characters from the input, |
|
348 | - * which might cause a raucous when trying to insert into the database |
|
349 | - * |
|
350 | - * @param string $request_data |
|
351 | - * @return string |
|
352 | - */ |
|
353 | - protected function _remove_unusable_characters($request_data) |
|
354 | - { |
|
355 | - return preg_replace('/[^[:print:]]/', '', $request_data); |
|
356 | - } |
|
357 | - |
|
358 | - |
|
359 | - |
|
360 | - /** |
|
361 | - * Should be called just before displaying the payment attempt results to the user, |
|
362 | - * when the payment attempt has finished. Some payment methods may have special |
|
363 | - * logic to perform here. For example, if process_payment() happens on a special request |
|
364 | - * and then the user is redirected to a page that displays the payment's status, this |
|
365 | - * should be called while loading the page that displays the payment's status. If the user is |
|
366 | - * sent to an offsite payment provider, this should be called upon returning from that offsite payment |
|
367 | - * provider. |
|
368 | - * |
|
369 | - * @param EE_Transaction|int $transaction |
|
370 | - * @param bool $update_txn whether or not to call |
|
371 | - * EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() |
|
372 | - * @throws \EE_Error |
|
373 | - * @return EE_Payment |
|
374 | - * @deprecated 4.6.24 method is no longer used. Instead it is up to client code, like SPCO, |
|
375 | - * to call handle_ipn() for offsite gateways that don't receive separate IPNs |
|
376 | - */ |
|
377 | - public function finalize_payment_for($transaction, $update_txn = true) |
|
378 | - { |
|
379 | - /** @var $transaction EE_Transaction */ |
|
380 | - $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
381 | - $last_payment_method = $transaction->payment_method(); |
|
382 | - if ($last_payment_method instanceof EE_Payment_Method) { |
|
383 | - $payment = $last_payment_method->type_obj()->finalize_payment_for($transaction); |
|
384 | - $this->update_txn_based_on_payment($transaction, $payment, $update_txn); |
|
385 | - return $payment; |
|
386 | - } else { |
|
387 | - return null; |
|
388 | - } |
|
389 | - } |
|
390 | - |
|
391 | - |
|
392 | - |
|
393 | - /** |
|
394 | - * Processes a direct refund request, saves the payment, and updates the transaction appropriately. |
|
395 | - * |
|
396 | - * @param EE_Payment_Method $payment_method |
|
397 | - * @param EE_Payment $payment_to_refund |
|
398 | - * @param array $refund_info |
|
399 | - * @return EE_Payment |
|
400 | - * @throws \EE_Error |
|
401 | - */ |
|
402 | - public function process_refund( |
|
403 | - EE_Payment_Method $payment_method, |
|
404 | - EE_Payment $payment_to_refund, |
|
405 | - $refund_info = array() |
|
406 | - ) { |
|
407 | - if ($payment_method instanceof EE_Payment_Method && $payment_method->type_obj()->supports_sending_refunds()) { |
|
408 | - $payment_method->type_obj()->process_refund($payment_to_refund, $refund_info); |
|
409 | - $this->update_txn_based_on_payment($payment_to_refund->transaction(), $payment_to_refund); |
|
410 | - } |
|
411 | - return $payment_to_refund; |
|
412 | - } |
|
413 | - |
|
414 | - |
|
415 | - |
|
416 | - /** |
|
417 | - * This should be called each time there may have been an update to a |
|
418 | - * payment on a transaction (ie, we asked for a payment to process a |
|
419 | - * payment for a transaction, or we told a payment method about an IPN, or |
|
420 | - * we told a payment method to |
|
421 | - * "finalize_payment_for" (a transaction), or we told a payment method to |
|
422 | - * process a refund. This should handle firing the correct hooks to |
|
423 | - * indicate |
|
424 | - * what exactly happened and updating the transaction appropriately). This |
|
425 | - * could be integrated directly into EE_Transaction upon save, but we want |
|
426 | - * this logic to be separate from 'normal' plain-jane saving and updating |
|
427 | - * of transactions and payments, and to be tied to payment processing. |
|
428 | - * Note: this method DOES NOT save the payment passed into it. It is the responsibility |
|
429 | - * of previous code to decide whether or not to save (because the payment passed into |
|
430 | - * this method might be a temporary, never-to-be-saved payment from an offline gateway, |
|
431 | - * in which case we only want that payment object for some temporary usage during this request, |
|
432 | - * but we don't want it to be saved). |
|
433 | - * |
|
434 | - * @param EE_Transaction|int $transaction |
|
435 | - * @param EE_Payment $payment |
|
436 | - * @param boolean $update_txn |
|
437 | - * whether or not to call |
|
438 | - * EE_Transaction_Processor:: |
|
439 | - * update_transaction_and_registrations_after_checkout_or_payment() |
|
440 | - * (you can save 1 DB query if you know you're going |
|
441 | - * to save it later instead) |
|
442 | - * @param bool $IPN |
|
443 | - * if processing IPNs or other similar payment |
|
444 | - * related activities that occur in alternate |
|
445 | - * requests than the main one that is processing the |
|
446 | - * TXN, then set this to true to check whether the |
|
447 | - * TXN is locked before updating |
|
448 | - * @throws \EE_Error |
|
449 | - */ |
|
450 | - public function update_txn_based_on_payment($transaction, $payment, $update_txn = true, $IPN = false) |
|
451 | - { |
|
452 | - $do_action = 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__not_successful'; |
|
453 | - /** @type EE_Transaction $transaction */ |
|
454 | - $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
455 | - // can we freely update the TXN at this moment? |
|
456 | - if ($IPN && $transaction->is_locked()) { |
|
457 | - // don't update the transaction at this exact moment |
|
458 | - // because the TXN is active in another request |
|
459 | - EE_Cron_Tasks::schedule_update_transaction_with_payment( |
|
460 | - time(), |
|
461 | - $transaction->ID(), |
|
462 | - $payment->ID() |
|
463 | - ); |
|
464 | - } else { |
|
465 | - // verify payment and that it has been saved |
|
466 | - if ($payment instanceof EE_Payment && $payment->ID()) { |
|
467 | - if ( |
|
468 | - $payment->payment_method() instanceof EE_Payment_Method |
|
469 | - && $payment->payment_method()->type_obj() instanceof EE_PMT_Base |
|
470 | - ) { |
|
471 | - $payment->payment_method()->type_obj()->update_txn_based_on_payment($payment); |
|
472 | - // update TXN registrations with payment info |
|
473 | - $this->process_registration_payments($transaction, $payment); |
|
474 | - } |
|
475 | - $do_action = $payment->just_approved() |
|
476 | - ? 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__successful' |
|
477 | - : $do_action; |
|
478 | - } else { |
|
479 | - // send out notifications |
|
480 | - add_filter('FHEE__EED_Messages___maybe_registration__deliver_notifications', '__return_true'); |
|
481 | - $do_action = 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__no_payment_made'; |
|
482 | - } |
|
483 | - if ($payment instanceof EE_Payment && $payment->status() !== EEM_Payment::status_id_failed) { |
|
484 | - /** @type EE_Transaction_Payments $transaction_payments */ |
|
485 | - $transaction_payments = EE_Registry::instance()->load_class('Transaction_Payments'); |
|
486 | - // set new value for total paid |
|
487 | - $transaction_payments->calculate_total_payments_and_update_status($transaction); |
|
488 | - // call EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() ??? |
|
489 | - if ($update_txn) { |
|
490 | - $this->_post_payment_processing($transaction, $payment, $IPN); |
|
491 | - } |
|
492 | - } |
|
493 | - // granular hook for others to use. |
|
494 | - do_action($do_action, $transaction, $payment); |
|
495 | - do_action('AHEE_log', __CLASS__, __FUNCTION__, $do_action, '$do_action'); |
|
496 | - //global hook for others to use. |
|
497 | - do_action('AHEE__EE_Payment_Processor__update_txn_based_on_payment', $transaction, $payment); |
|
498 | - } |
|
499 | - } |
|
500 | - |
|
501 | - |
|
502 | - |
|
503 | - /** |
|
504 | - * update registrations REG_paid field after successful payment and link registrations with payment |
|
505 | - * |
|
506 | - * @param EE_Transaction $transaction |
|
507 | - * @param EE_Payment $payment |
|
508 | - * @param EE_Registration[] $registrations |
|
509 | - * @throws \EE_Error |
|
510 | - */ |
|
511 | - public function process_registration_payments( |
|
512 | - EE_Transaction $transaction, |
|
513 | - EE_Payment $payment, |
|
514 | - $registrations = array() |
|
515 | - ) { |
|
516 | - // only process if payment was successful |
|
517 | - if ($payment->status() !== EEM_Payment::status_id_approved) { |
|
518 | - return; |
|
519 | - } |
|
520 | - //EEM_Registration::instance()->show_next_x_db_queries(); |
|
521 | - if (empty($registrations)) { |
|
522 | - // find registrations with monies owing that can receive a payment |
|
523 | - $registrations = $transaction->registrations( |
|
524 | - array( |
|
525 | - array( |
|
526 | - // only these reg statuses can receive payments |
|
527 | - 'STS_ID' => array('IN', EEM_Registration::reg_statuses_that_allow_payment()), |
|
528 | - 'REG_final_price' => array('!=', 0), |
|
529 | - 'REG_final_price*' => array('!=', 'REG_paid', true), |
|
530 | - ), |
|
531 | - ) |
|
532 | - ); |
|
533 | - } |
|
534 | - // still nothing ??!?? |
|
535 | - if (empty($registrations)) { |
|
536 | - return; |
|
537 | - } |
|
538 | - // todo: break out the following logic into a separate strategy class |
|
539 | - // todo: named something like "Sequential_Reg_Payment_Strategy" |
|
540 | - // todo: which would apply payments using the capitalist "first come first paid" approach |
|
541 | - // todo: then have another strategy class like "Distributed_Reg_Payment_Strategy" |
|
542 | - // todo: which would be the socialist "everybody gets a piece of pie" approach, |
|
543 | - // todo: which would be better for deposits, where you want a bit of the payment applied to each registration |
|
544 | - $refund = $payment->is_a_refund(); |
|
545 | - // how much is available to apply to registrations? |
|
546 | - $available_payment_amount = abs($payment->amount()); |
|
547 | - foreach ($registrations as $registration) { |
|
548 | - if ($registration instanceof EE_Registration) { |
|
549 | - // nothing left? |
|
550 | - if ($available_payment_amount <= 0) { |
|
551 | - break; |
|
552 | - } |
|
553 | - if ($refund) { |
|
554 | - $available_payment_amount = $this->process_registration_refund($registration, $payment, $available_payment_amount); |
|
555 | - } else { |
|
556 | - $available_payment_amount = $this->process_registration_payment($registration, $payment, $available_payment_amount); |
|
557 | - } |
|
558 | - } |
|
559 | - } |
|
560 | - if ($available_payment_amount > 0 && apply_filters('FHEE__EE_Payment_Processor__process_registration_payments__display_notifications', false)) { |
|
561 | - EE_Error::add_attention( |
|
562 | - sprintf( |
|
563 | - __('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).', |
|
564 | - 'event_espresso'), |
|
565 | - EEH_Template::format_currency($available_payment_amount), |
|
566 | - implode(', ', array_keys($registrations)), |
|
567 | - '<br/>', |
|
568 | - EEH_Template::format_currency($payment->amount()) |
|
569 | - ), |
|
570 | - __FILE__, __FUNCTION__, __LINE__ |
|
571 | - ); |
|
572 | - } |
|
573 | - } |
|
574 | - |
|
575 | - |
|
576 | - |
|
577 | - /** |
|
578 | - * update registration REG_paid field after successful payment and link registration with payment |
|
579 | - * |
|
580 | - * @param EE_Registration $registration |
|
581 | - * @param EE_Payment $payment |
|
582 | - * @param float $available_payment_amount |
|
583 | - * @return float |
|
584 | - * @throws \EE_Error |
|
585 | - */ |
|
586 | - public function process_registration_payment( |
|
587 | - EE_Registration $registration, |
|
588 | - EE_Payment $payment, |
|
589 | - $available_payment_amount = 0.00 |
|
590 | - ) { |
|
591 | - $owing = $registration->final_price() - $registration->paid(); |
|
592 | - if ($owing > 0) { |
|
593 | - // don't allow payment amount to exceed the available payment amount, OR the amount owing |
|
594 | - $payment_amount = min($available_payment_amount, $owing); |
|
595 | - // update $available_payment_amount |
|
596 | - $available_payment_amount -= $payment_amount; |
|
597 | - //calculate and set new REG_paid |
|
598 | - $registration->set_paid($registration->paid() + $payment_amount); |
|
599 | - // now save it |
|
600 | - $this->_apply_registration_payment($registration, $payment, $payment_amount); |
|
601 | - } |
|
602 | - return $available_payment_amount; |
|
603 | - } |
|
604 | - |
|
605 | - |
|
606 | - |
|
607 | - /** |
|
608 | - * update registration REG_paid field after successful payment and link registration with payment |
|
609 | - * |
|
610 | - * @param EE_Registration $registration |
|
611 | - * @param EE_Payment $payment |
|
612 | - * @param float $payment_amount |
|
613 | - * @return void |
|
614 | - * @throws \EE_Error |
|
615 | - */ |
|
616 | - protected function _apply_registration_payment( |
|
617 | - EE_Registration $registration, |
|
618 | - EE_Payment $payment, |
|
619 | - $payment_amount = 0.00 |
|
620 | - ) { |
|
621 | - // find any existing reg payment records for this registration and payment |
|
622 | - $existing_reg_payment = EEM_Registration_Payment::instance()->get_one( |
|
623 | - array(array('REG_ID' => $registration->ID(), 'PAY_ID' => $payment->ID())) |
|
624 | - ); |
|
625 | - // if existing registration payment exists |
|
626 | - if ($existing_reg_payment instanceof EE_Registration_Payment) { |
|
627 | - // then update that record |
|
628 | - $existing_reg_payment->set_amount($payment_amount); |
|
629 | - $existing_reg_payment->save(); |
|
630 | - } else { |
|
631 | - // or add new relation between registration and payment and set amount |
|
632 | - $registration->_add_relation_to($payment, 'Payment', array('RPY_amount' => $payment_amount)); |
|
633 | - // make it stick |
|
634 | - $registration->save(); |
|
635 | - } |
|
636 | - } |
|
637 | - |
|
638 | - |
|
639 | - |
|
640 | - /** |
|
641 | - * update registration REG_paid field after refund and link registration with payment |
|
642 | - * |
|
643 | - * @param EE_Registration $registration |
|
644 | - * @param EE_Payment $payment |
|
645 | - * @param float $available_refund_amount - IMPORTANT !!! SEND AVAILABLE REFUND AMOUNT AS A POSITIVE NUMBER |
|
646 | - * @return float |
|
647 | - * @throws \EE_Error |
|
648 | - */ |
|
649 | - public function process_registration_refund( |
|
650 | - EE_Registration $registration, |
|
651 | - EE_Payment $payment, |
|
652 | - $available_refund_amount = 0.00 |
|
653 | - ) { |
|
654 | - //EEH_Debug_Tools::printr( $payment->amount(), '$payment->amount()', __FILE__, __LINE__ ); |
|
655 | - if ($registration->paid() > 0) { |
|
656 | - // ensure $available_refund_amount is NOT negative |
|
657 | - $available_refund_amount = (float)abs($available_refund_amount); |
|
658 | - // don't allow refund amount to exceed the available payment amount, OR the amount paid |
|
659 | - $refund_amount = min($available_refund_amount, (float)$registration->paid()); |
|
660 | - // update $available_payment_amount |
|
661 | - $available_refund_amount -= $refund_amount; |
|
662 | - //calculate and set new REG_paid |
|
663 | - $registration->set_paid($registration->paid() - $refund_amount); |
|
664 | - // convert payment amount back to a negative value for storage in the db |
|
665 | - $refund_amount = (float)abs($refund_amount) * -1; |
|
666 | - // now save it |
|
667 | - $this->_apply_registration_payment($registration, $payment, $refund_amount); |
|
668 | - } |
|
669 | - return $available_refund_amount; |
|
670 | - } |
|
671 | - |
|
672 | - |
|
673 | - |
|
674 | - /** |
|
675 | - * Process payments and transaction after payment process completed. |
|
676 | - * ultimately this will send the TXN and payment details off so that notifications can be sent out. |
|
677 | - * if this request happens to be processing an IPN, |
|
678 | - * then we will also set the Payment Options Reg Step to completed, |
|
679 | - * and attempt to completely finalize the TXN if all of the other Reg Steps are completed as well. |
|
680 | - * |
|
681 | - * @param EE_Transaction $transaction |
|
682 | - * @param EE_Payment $payment |
|
683 | - * @param bool $IPN |
|
684 | - * @throws \EE_Error |
|
685 | - */ |
|
686 | - protected function _post_payment_processing(EE_Transaction $transaction, EE_Payment $payment, $IPN = false) |
|
687 | - { |
|
688 | - /** @type EE_Transaction_Processor $transaction_processor */ |
|
689 | - $transaction_processor = EE_Registry::instance()->load_class('Transaction_Processor'); |
|
690 | - // is the Payment Options Reg Step completed ? |
|
691 | - $payment_options_step_completed = $transaction->reg_step_completed('payment_options'); |
|
692 | - // if the Payment Options Reg Step is completed... |
|
693 | - $revisit = $payment_options_step_completed === true ? true : false; |
|
694 | - // then this is kinda sorta a revisit with regards to payments at least |
|
695 | - $transaction_processor->set_revisit($revisit); |
|
696 | - // if this is an IPN, let's consider the Payment Options Reg Step completed if not already |
|
697 | - if ( |
|
698 | - $IPN |
|
699 | - && $payment_options_step_completed !== true |
|
700 | - && ($payment->is_approved() || $payment->is_pending()) |
|
701 | - ) { |
|
702 | - $payment_options_step_completed = $transaction->set_reg_step_completed( |
|
703 | - 'payment_options' |
|
704 | - ); |
|
705 | - } |
|
706 | - // maybe update status, but don't save transaction just yet |
|
707 | - $transaction->update_status_based_on_total_paid(false); |
|
708 | - // check if 'finalize_registration' step has been completed... |
|
709 | - $finalized = $transaction->reg_step_completed('finalize_registration'); |
|
710 | - // if this is an IPN and the final step has not been initiated |
|
711 | - if ($IPN && $payment_options_step_completed && $finalized === false) { |
|
712 | - // and if it hasn't already been set as being started... |
|
713 | - $finalized = $transaction->set_reg_step_initiated('finalize_registration'); |
|
714 | - } |
|
715 | - $transaction->save(); |
|
716 | - // because the above will return false if the final step was not fully completed, we need to check again... |
|
717 | - if ($IPN && $finalized !== false) { |
|
718 | - // and if we are all good to go, then send out notifications |
|
719 | - add_filter('FHEE__EED_Messages___maybe_registration__deliver_notifications', '__return_true'); |
|
720 | - //ok, now process the transaction according to the payment |
|
721 | - $transaction_processor->update_transaction_and_registrations_after_checkout_or_payment($transaction, $payment); |
|
722 | - } |
|
723 | - // DEBUG LOG |
|
724 | - $payment_method = $payment->payment_method(); |
|
725 | - if ($payment_method instanceof EE_Payment_Method) { |
|
726 | - $payment_method_type_obj = $payment_method->type_obj(); |
|
727 | - if ($payment_method_type_obj instanceof EE_PMT_Base) { |
|
728 | - $gateway = $payment_method_type_obj->get_gateway(); |
|
729 | - if ($gateway instanceof EE_Gateway) { |
|
730 | - $gateway->log( |
|
731 | - array( |
|
732 | - 'message' => __('Post Payment Transaction Details', 'event_espresso'), |
|
733 | - 'transaction' => $transaction->model_field_array(), |
|
734 | - 'finalized' => $finalized, |
|
735 | - 'IPN' => $IPN, |
|
736 | - 'deliver_notifications' => has_filter( |
|
737 | - 'FHEE__EED_Messages___maybe_registration__deliver_notifications' |
|
738 | - ), |
|
739 | - ), |
|
740 | - $payment |
|
741 | - ); |
|
742 | - } |
|
743 | - } |
|
744 | - } |
|
745 | - } |
|
746 | - |
|
747 | - |
|
748 | - |
|
749 | - /** |
|
750 | - * Force posts to PayPal to use TLS v1.2. See: |
|
751 | - * https://core.trac.wordpress.org/ticket/36320 |
|
752 | - * https://core.trac.wordpress.org/ticket/34924#comment:15 |
|
753 | - * https://www.paypal-knowledge.com/infocenter/index?page=content&widgetview=true&id=FAQ1914&viewlocale=en_US |
|
754 | - * This will affect paypal standard, pro, express, and payflow. |
|
755 | - */ |
|
756 | - public static function _curl_requests_to_paypal_use_tls($handle, $r, $url) |
|
757 | - { |
|
758 | - if (strstr($url, 'https://') && strstr($url, '.paypal.com')) { |
|
759 | - //Use the value of the constant CURL_SSLVERSION_TLSv1 = 1 |
|
760 | - //instead of the constant because it might not be defined |
|
761 | - curl_setopt($handle, CURLOPT_SSLVERSION, 1); |
|
762 | - } |
|
763 | - } |
|
20 | + /** |
|
21 | + * @var EE_Payment_Processor $_instance |
|
22 | + * @access private |
|
23 | + */ |
|
24 | + private static $_instance; |
|
25 | + |
|
26 | + |
|
27 | + |
|
28 | + /** |
|
29 | + * @singleton method used to instantiate class object |
|
30 | + * @access public |
|
31 | + * @return EE_Payment_Processor instance |
|
32 | + */ |
|
33 | + public static function instance() |
|
34 | + { |
|
35 | + // check if class object is instantiated |
|
36 | + if ( ! self::$_instance instanceof EE_Payment_Processor) { |
|
37 | + self::$_instance = new self(); |
|
38 | + } |
|
39 | + return self::$_instance; |
|
40 | + } |
|
41 | + |
|
42 | + |
|
43 | + |
|
44 | + /** |
|
45 | + * @return EE_Payment_Processor |
|
46 | + */ |
|
47 | + public static function reset() |
|
48 | + { |
|
49 | + self::$_instance = null; |
|
50 | + return self::instance(); |
|
51 | + } |
|
52 | + |
|
53 | + |
|
54 | + |
|
55 | + /** |
|
56 | + *private constructor to prevent direct creation |
|
57 | + * |
|
58 | + * @Constructor |
|
59 | + * @access private |
|
60 | + */ |
|
61 | + private function __construct() |
|
62 | + { |
|
63 | + do_action('AHEE__EE_Payment_Processor__construct'); |
|
64 | + add_action('http_api_curl', array($this, '_curl_requests_to_paypal_use_tls'), 10, 3); |
|
65 | + } |
|
66 | + |
|
67 | + |
|
68 | + |
|
69 | + /** |
|
70 | + * Using the selected gateway, processes the payment for that transaction, and updates the transaction |
|
71 | + * appropriately. Saves the payment that is generated |
|
72 | + * |
|
73 | + * @param EE_Payment_Method $payment_method |
|
74 | + * @param EE_Transaction $transaction |
|
75 | + * @param float $amount if only part of the transaction is to be paid for, how much. |
|
76 | + * Leave null if payment is for the full amount owing |
|
77 | + * @param EE_Billing_Info_Form $billing_form (or probably null, if it's an offline or offsite payment method). |
|
78 | + * Receive_form_submission() should have |
|
79 | + * already been called on the billing form |
|
80 | + * (ie, its inputs should have their normalized values set). |
|
81 | + * @param string $return_url string used mostly by offsite gateways to specify |
|
82 | + * where to go AFTER the offsite gateway |
|
83 | + * @param string $method like 'CART', indicates who the client who called this was |
|
84 | + * @param bool $by_admin TRUE if payment is being attempted from the admin |
|
85 | + * @param boolean $update_txn whether or not to call |
|
86 | + * EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() |
|
87 | + * @param string $cancel_url URL to return to if off-site payments are cancelled |
|
88 | + * @return \EE_Payment |
|
89 | + * @throws \EE_Error |
|
90 | + */ |
|
91 | + public function process_payment( |
|
92 | + EE_Payment_Method $payment_method, |
|
93 | + EE_Transaction $transaction, |
|
94 | + $amount = null, |
|
95 | + $billing_form = null, |
|
96 | + $return_url = null, |
|
97 | + $method = 'CART', |
|
98 | + $by_admin = false, |
|
99 | + $update_txn = true, |
|
100 | + $cancel_url = '' |
|
101 | + ) { |
|
102 | + if ((float)$amount < 0) { |
|
103 | + throw new EE_Error( |
|
104 | + sprintf( |
|
105 | + __( |
|
106 | + 'Attempting to make a payment for a negative amount of %1$d for transaction %2$d. That should be a refund', |
|
107 | + 'event_espresso' |
|
108 | + ), |
|
109 | + $amount, |
|
110 | + $transaction->ID() |
|
111 | + ) |
|
112 | + ); |
|
113 | + } |
|
114 | + // verify payment method |
|
115 | + $payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method, true); |
|
116 | + // verify transaction |
|
117 | + EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
118 | + $transaction->set_payment_method_ID($payment_method->ID()); |
|
119 | + // verify payment method type |
|
120 | + if ($payment_method->type_obj() instanceof EE_PMT_Base) { |
|
121 | + $payment = $payment_method->type_obj()->process_payment( |
|
122 | + $transaction, |
|
123 | + min($amount, $transaction->remaining()),//make sure we don't overcharge |
|
124 | + $billing_form, |
|
125 | + $return_url, |
|
126 | + add_query_arg(array('ee_cancel_payment' => true), $cancel_url), |
|
127 | + $method, |
|
128 | + $by_admin |
|
129 | + ); |
|
130 | + // check if payment method uses an off-site gateway |
|
131 | + if ($payment_method->type_obj()->payment_occurs() !== EE_PMT_Base::offsite) { |
|
132 | + // don't process payments for off-site gateways yet because no payment has occurred yet |
|
133 | + $this->update_txn_based_on_payment($transaction, $payment, $update_txn); |
|
134 | + } |
|
135 | + return $payment; |
|
136 | + } else { |
|
137 | + EE_Error::add_error( |
|
138 | + sprintf( |
|
139 | + __('A valid payment method could not be determined due to a technical issue.%sPlease try again or contact %s for assistance.', 'event_espresso'), |
|
140 | + '<br/>', |
|
141 | + EE_Registry::instance()->CFG->organization->get_pretty('email') |
|
142 | + ), __FILE__, __FUNCTION__, __LINE__ |
|
143 | + ); |
|
144 | + return null; |
|
145 | + } |
|
146 | + } |
|
147 | + |
|
148 | + |
|
149 | + |
|
150 | + /** |
|
151 | + * @param EE_Transaction|int $transaction |
|
152 | + * @param EE_Payment_Method $payment_method |
|
153 | + * @throws EE_Error |
|
154 | + * @return string |
|
155 | + */ |
|
156 | + public function get_ipn_url_for_payment_method($transaction, $payment_method) |
|
157 | + { |
|
158 | + /** @type \EE_Transaction $transaction */ |
|
159 | + $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
160 | + $primary_reg = $transaction->primary_registration(); |
|
161 | + if ( ! $primary_reg instanceof EE_Registration) { |
|
162 | + throw new EE_Error( |
|
163 | + sprintf( |
|
164 | + __( |
|
165 | + "Cannot get IPN URL for transaction with ID %d because it has no primary registration", |
|
166 | + "event_espresso" |
|
167 | + ), |
|
168 | + $transaction->ID() |
|
169 | + ) |
|
170 | + ); |
|
171 | + } |
|
172 | + $payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method, true); |
|
173 | + $url = add_query_arg( |
|
174 | + array( |
|
175 | + 'e_reg_url_link' => $primary_reg->reg_url_link(), |
|
176 | + 'ee_payment_method' => $payment_method->slug(), |
|
177 | + ), |
|
178 | + EE_Registry::instance()->CFG->core->txn_page_url() |
|
179 | + ); |
|
180 | + return $url; |
|
181 | + } |
|
182 | + |
|
183 | + |
|
184 | + |
|
185 | + /** |
|
186 | + * Process the IPN. Firstly, we'll hope we put the standard args into the IPN URL so |
|
187 | + * we can easily find what registration the IPN is for and what payment method. |
|
188 | + * However, if not, we'll give all payment methods a chance to claim it and process it. |
|
189 | + * If a payment is found for the IPN info, it is saved. |
|
190 | + * |
|
191 | + * @param array $_req_data eg $_REQUEST |
|
192 | + * @param EE_Transaction|int $transaction optional (or a transactions id) |
|
193 | + * @param EE_Payment_Method $payment_method (or a slug or id of one) |
|
194 | + * @param boolean $update_txn whether or not to call |
|
195 | + * EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() |
|
196 | + * @param bool $separate_IPN_request whether the IPN uses a separate request ( true like PayPal ) |
|
197 | + * or is processed manually ( false like Mijireh ) |
|
198 | + * @throws EE_Error |
|
199 | + * @throws Exception |
|
200 | + * @return EE_Payment |
|
201 | + */ |
|
202 | + public function process_ipn( |
|
203 | + $_req_data, |
|
204 | + $transaction = null, |
|
205 | + $payment_method = null, |
|
206 | + $update_txn = true, |
|
207 | + $separate_IPN_request = true |
|
208 | + ) { |
|
209 | + EE_Registry::instance()->load_model('Change_Log'); |
|
210 | + $_req_data = $this->_remove_unusable_characters_from_array((array)$_req_data); |
|
211 | + EE_Processor_Base::set_IPN($separate_IPN_request); |
|
212 | + $obj_for_log = null; |
|
213 | + if ($transaction instanceof EE_Transaction) { |
|
214 | + $obj_for_log = $transaction; |
|
215 | + if ($payment_method instanceof EE_Payment_Method) { |
|
216 | + $obj_for_log = EEM_Payment::instance()->get_one( |
|
217 | + array( |
|
218 | + array('TXN_ID' => $transaction->ID(), 'PMD_ID' => $payment_method->ID()), |
|
219 | + 'order_by' => array('PAY_timestamp' => 'desc'), |
|
220 | + ) |
|
221 | + ); |
|
222 | + } |
|
223 | + } else if ($payment_method instanceof EE_Payment) { |
|
224 | + $obj_for_log = $payment_method; |
|
225 | + } |
|
226 | + $log = EEM_Change_Log::instance()->log( |
|
227 | + EEM_Change_Log::type_gateway, |
|
228 | + array('IPN data received' => $_req_data), |
|
229 | + $obj_for_log |
|
230 | + ); |
|
231 | + try { |
|
232 | + /** |
|
233 | + * @var EE_Payment $payment |
|
234 | + */ |
|
235 | + $payment = null; |
|
236 | + if ($transaction && $payment_method) { |
|
237 | + /** @type EE_Transaction $transaction */ |
|
238 | + $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
239 | + /** @type EE_Payment_Method $payment_method */ |
|
240 | + $payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method); |
|
241 | + if ($payment_method->type_obj() instanceof EE_PMT_Base) { |
|
242 | + try { |
|
243 | + $payment = $payment_method->type_obj()->handle_ipn($_req_data, $transaction); |
|
244 | + $log->set_object($payment); |
|
245 | + } catch (EventEspresso\core\exceptions\IpnException $e) { |
|
246 | + EEM_Change_Log::instance()->log( |
|
247 | + EEM_Change_Log::type_gateway, |
|
248 | + array( |
|
249 | + 'message' => 'IPN Exception: ' . $e->getMessage(), |
|
250 | + 'current_url' => EEH_URL::current_url(), |
|
251 | + 'payment' => $e->getPaymentProperties(), |
|
252 | + 'IPN_data' => $e->getIpnData(), |
|
253 | + ), |
|
254 | + $obj_for_log |
|
255 | + ); |
|
256 | + return $e->getPayment(); |
|
257 | + } |
|
258 | + } else { |
|
259 | + // not a payment |
|
260 | + EE_Error::add_error( |
|
261 | + sprintf( |
|
262 | + __('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'), |
|
263 | + '<br/>', |
|
264 | + EE_Registry::instance()->CFG->organization->get_pretty('email') |
|
265 | + ), |
|
266 | + __FILE__, __FUNCTION__, __LINE__ |
|
267 | + ); |
|
268 | + } |
|
269 | + } else { |
|
270 | + //that's actually pretty ok. The IPN just wasn't able |
|
271 | + //to identify which transaction or payment method this was for |
|
272 | + // give all active payment methods a chance to claim it |
|
273 | + $active_payment_methods = EEM_Payment_Method::instance()->get_all_active(); |
|
274 | + foreach ($active_payment_methods as $active_payment_method) { |
|
275 | + try { |
|
276 | + $payment = $active_payment_method->type_obj()->handle_unclaimed_ipn($_req_data); |
|
277 | + $payment_method = $active_payment_method; |
|
278 | + EEM_Change_Log::instance()->log( |
|
279 | + EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $payment |
|
280 | + ); |
|
281 | + break; |
|
282 | + } catch (EventEspresso\core\exceptions\IpnException $e) { |
|
283 | + EEM_Change_Log::instance()->log( |
|
284 | + EEM_Change_Log::type_gateway, |
|
285 | + array( |
|
286 | + 'message' => 'IPN Exception: ' . $e->getMessage(), |
|
287 | + 'current_url' => EEH_URL::current_url(), |
|
288 | + 'payment' => $e->getPaymentProperties(), |
|
289 | + 'IPN_data' => $e->getIpnData(), |
|
290 | + ), |
|
291 | + $obj_for_log |
|
292 | + ); |
|
293 | + return $e->getPayment(); |
|
294 | + } catch (EE_Error $e) { |
|
295 | + //that's fine- it apparently couldn't handle the IPN |
|
296 | + } |
|
297 | + } |
|
298 | + } |
|
299 | + // EEM_Payment_Log::instance()->log("got to 7",$transaction,$payment_method); |
|
300 | + if ($payment instanceof EE_Payment) { |
|
301 | + $payment->save(); |
|
302 | + // update the TXN |
|
303 | + $this->update_txn_based_on_payment($transaction, $payment, $update_txn, $separate_IPN_request); |
|
304 | + } else { |
|
305 | + //we couldn't find the payment for this IPN... let's try and log at least SOMETHING |
|
306 | + if ($payment_method) { |
|
307 | + EEM_Change_Log::instance()->log(EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $payment_method); |
|
308 | + } elseif ($transaction) { |
|
309 | + EEM_Change_Log::instance()->log(EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $transaction); |
|
310 | + } |
|
311 | + } |
|
312 | + return $payment; |
|
313 | + } catch (EE_Error $e) { |
|
314 | + do_action( |
|
315 | + 'AHEE__log', __FILE__, __FUNCTION__, sprintf( |
|
316 | + __('Error occurred while receiving IPN. Transaction: %1$s, req data: %2$s. The error was "%3$s"', 'event_espresso'), |
|
317 | + print_r($transaction, true), |
|
318 | + print_r($_req_data, true), |
|
319 | + $e->getMessage() |
|
320 | + ) |
|
321 | + ); |
|
322 | + throw $e; |
|
323 | + } |
|
324 | + } |
|
325 | + |
|
326 | + |
|
327 | + |
|
328 | + /** |
|
329 | + * Removes any non-printable illegal characters from the input, |
|
330 | + * which might cause a raucous when trying to insert into the database |
|
331 | + * |
|
332 | + * @param array $request_data |
|
333 | + * @return array |
|
334 | + */ |
|
335 | + protected function _remove_unusable_characters_from_array(array $request_data) |
|
336 | + { |
|
337 | + $return_data = array(); |
|
338 | + foreach ($request_data as $key => $value) { |
|
339 | + $return_data[$this->_remove_unusable_characters($key)] = $this->_remove_unusable_characters($value); |
|
340 | + } |
|
341 | + return $return_data; |
|
342 | + } |
|
343 | + |
|
344 | + |
|
345 | + |
|
346 | + /** |
|
347 | + * Removes any non-printable illegal characters from the input, |
|
348 | + * which might cause a raucous when trying to insert into the database |
|
349 | + * |
|
350 | + * @param string $request_data |
|
351 | + * @return string |
|
352 | + */ |
|
353 | + protected function _remove_unusable_characters($request_data) |
|
354 | + { |
|
355 | + return preg_replace('/[^[:print:]]/', '', $request_data); |
|
356 | + } |
|
357 | + |
|
358 | + |
|
359 | + |
|
360 | + /** |
|
361 | + * Should be called just before displaying the payment attempt results to the user, |
|
362 | + * when the payment attempt has finished. Some payment methods may have special |
|
363 | + * logic to perform here. For example, if process_payment() happens on a special request |
|
364 | + * and then the user is redirected to a page that displays the payment's status, this |
|
365 | + * should be called while loading the page that displays the payment's status. If the user is |
|
366 | + * sent to an offsite payment provider, this should be called upon returning from that offsite payment |
|
367 | + * provider. |
|
368 | + * |
|
369 | + * @param EE_Transaction|int $transaction |
|
370 | + * @param bool $update_txn whether or not to call |
|
371 | + * EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() |
|
372 | + * @throws \EE_Error |
|
373 | + * @return EE_Payment |
|
374 | + * @deprecated 4.6.24 method is no longer used. Instead it is up to client code, like SPCO, |
|
375 | + * to call handle_ipn() for offsite gateways that don't receive separate IPNs |
|
376 | + */ |
|
377 | + public function finalize_payment_for($transaction, $update_txn = true) |
|
378 | + { |
|
379 | + /** @var $transaction EE_Transaction */ |
|
380 | + $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
381 | + $last_payment_method = $transaction->payment_method(); |
|
382 | + if ($last_payment_method instanceof EE_Payment_Method) { |
|
383 | + $payment = $last_payment_method->type_obj()->finalize_payment_for($transaction); |
|
384 | + $this->update_txn_based_on_payment($transaction, $payment, $update_txn); |
|
385 | + return $payment; |
|
386 | + } else { |
|
387 | + return null; |
|
388 | + } |
|
389 | + } |
|
390 | + |
|
391 | + |
|
392 | + |
|
393 | + /** |
|
394 | + * Processes a direct refund request, saves the payment, and updates the transaction appropriately. |
|
395 | + * |
|
396 | + * @param EE_Payment_Method $payment_method |
|
397 | + * @param EE_Payment $payment_to_refund |
|
398 | + * @param array $refund_info |
|
399 | + * @return EE_Payment |
|
400 | + * @throws \EE_Error |
|
401 | + */ |
|
402 | + public function process_refund( |
|
403 | + EE_Payment_Method $payment_method, |
|
404 | + EE_Payment $payment_to_refund, |
|
405 | + $refund_info = array() |
|
406 | + ) { |
|
407 | + if ($payment_method instanceof EE_Payment_Method && $payment_method->type_obj()->supports_sending_refunds()) { |
|
408 | + $payment_method->type_obj()->process_refund($payment_to_refund, $refund_info); |
|
409 | + $this->update_txn_based_on_payment($payment_to_refund->transaction(), $payment_to_refund); |
|
410 | + } |
|
411 | + return $payment_to_refund; |
|
412 | + } |
|
413 | + |
|
414 | + |
|
415 | + |
|
416 | + /** |
|
417 | + * This should be called each time there may have been an update to a |
|
418 | + * payment on a transaction (ie, we asked for a payment to process a |
|
419 | + * payment for a transaction, or we told a payment method about an IPN, or |
|
420 | + * we told a payment method to |
|
421 | + * "finalize_payment_for" (a transaction), or we told a payment method to |
|
422 | + * process a refund. This should handle firing the correct hooks to |
|
423 | + * indicate |
|
424 | + * what exactly happened and updating the transaction appropriately). This |
|
425 | + * could be integrated directly into EE_Transaction upon save, but we want |
|
426 | + * this logic to be separate from 'normal' plain-jane saving and updating |
|
427 | + * of transactions and payments, and to be tied to payment processing. |
|
428 | + * Note: this method DOES NOT save the payment passed into it. It is the responsibility |
|
429 | + * of previous code to decide whether or not to save (because the payment passed into |
|
430 | + * this method might be a temporary, never-to-be-saved payment from an offline gateway, |
|
431 | + * in which case we only want that payment object for some temporary usage during this request, |
|
432 | + * but we don't want it to be saved). |
|
433 | + * |
|
434 | + * @param EE_Transaction|int $transaction |
|
435 | + * @param EE_Payment $payment |
|
436 | + * @param boolean $update_txn |
|
437 | + * whether or not to call |
|
438 | + * EE_Transaction_Processor:: |
|
439 | + * update_transaction_and_registrations_after_checkout_or_payment() |
|
440 | + * (you can save 1 DB query if you know you're going |
|
441 | + * to save it later instead) |
|
442 | + * @param bool $IPN |
|
443 | + * if processing IPNs or other similar payment |
|
444 | + * related activities that occur in alternate |
|
445 | + * requests than the main one that is processing the |
|
446 | + * TXN, then set this to true to check whether the |
|
447 | + * TXN is locked before updating |
|
448 | + * @throws \EE_Error |
|
449 | + */ |
|
450 | + public function update_txn_based_on_payment($transaction, $payment, $update_txn = true, $IPN = false) |
|
451 | + { |
|
452 | + $do_action = 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__not_successful'; |
|
453 | + /** @type EE_Transaction $transaction */ |
|
454 | + $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
455 | + // can we freely update the TXN at this moment? |
|
456 | + if ($IPN && $transaction->is_locked()) { |
|
457 | + // don't update the transaction at this exact moment |
|
458 | + // because the TXN is active in another request |
|
459 | + EE_Cron_Tasks::schedule_update_transaction_with_payment( |
|
460 | + time(), |
|
461 | + $transaction->ID(), |
|
462 | + $payment->ID() |
|
463 | + ); |
|
464 | + } else { |
|
465 | + // verify payment and that it has been saved |
|
466 | + if ($payment instanceof EE_Payment && $payment->ID()) { |
|
467 | + if ( |
|
468 | + $payment->payment_method() instanceof EE_Payment_Method |
|
469 | + && $payment->payment_method()->type_obj() instanceof EE_PMT_Base |
|
470 | + ) { |
|
471 | + $payment->payment_method()->type_obj()->update_txn_based_on_payment($payment); |
|
472 | + // update TXN registrations with payment info |
|
473 | + $this->process_registration_payments($transaction, $payment); |
|
474 | + } |
|
475 | + $do_action = $payment->just_approved() |
|
476 | + ? 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__successful' |
|
477 | + : $do_action; |
|
478 | + } else { |
|
479 | + // send out notifications |
|
480 | + add_filter('FHEE__EED_Messages___maybe_registration__deliver_notifications', '__return_true'); |
|
481 | + $do_action = 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__no_payment_made'; |
|
482 | + } |
|
483 | + if ($payment instanceof EE_Payment && $payment->status() !== EEM_Payment::status_id_failed) { |
|
484 | + /** @type EE_Transaction_Payments $transaction_payments */ |
|
485 | + $transaction_payments = EE_Registry::instance()->load_class('Transaction_Payments'); |
|
486 | + // set new value for total paid |
|
487 | + $transaction_payments->calculate_total_payments_and_update_status($transaction); |
|
488 | + // call EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() ??? |
|
489 | + if ($update_txn) { |
|
490 | + $this->_post_payment_processing($transaction, $payment, $IPN); |
|
491 | + } |
|
492 | + } |
|
493 | + // granular hook for others to use. |
|
494 | + do_action($do_action, $transaction, $payment); |
|
495 | + do_action('AHEE_log', __CLASS__, __FUNCTION__, $do_action, '$do_action'); |
|
496 | + //global hook for others to use. |
|
497 | + do_action('AHEE__EE_Payment_Processor__update_txn_based_on_payment', $transaction, $payment); |
|
498 | + } |
|
499 | + } |
|
500 | + |
|
501 | + |
|
502 | + |
|
503 | + /** |
|
504 | + * update registrations REG_paid field after successful payment and link registrations with payment |
|
505 | + * |
|
506 | + * @param EE_Transaction $transaction |
|
507 | + * @param EE_Payment $payment |
|
508 | + * @param EE_Registration[] $registrations |
|
509 | + * @throws \EE_Error |
|
510 | + */ |
|
511 | + public function process_registration_payments( |
|
512 | + EE_Transaction $transaction, |
|
513 | + EE_Payment $payment, |
|
514 | + $registrations = array() |
|
515 | + ) { |
|
516 | + // only process if payment was successful |
|
517 | + if ($payment->status() !== EEM_Payment::status_id_approved) { |
|
518 | + return; |
|
519 | + } |
|
520 | + //EEM_Registration::instance()->show_next_x_db_queries(); |
|
521 | + if (empty($registrations)) { |
|
522 | + // find registrations with monies owing that can receive a payment |
|
523 | + $registrations = $transaction->registrations( |
|
524 | + array( |
|
525 | + array( |
|
526 | + // only these reg statuses can receive payments |
|
527 | + 'STS_ID' => array('IN', EEM_Registration::reg_statuses_that_allow_payment()), |
|
528 | + 'REG_final_price' => array('!=', 0), |
|
529 | + 'REG_final_price*' => array('!=', 'REG_paid', true), |
|
530 | + ), |
|
531 | + ) |
|
532 | + ); |
|
533 | + } |
|
534 | + // still nothing ??!?? |
|
535 | + if (empty($registrations)) { |
|
536 | + return; |
|
537 | + } |
|
538 | + // todo: break out the following logic into a separate strategy class |
|
539 | + // todo: named something like "Sequential_Reg_Payment_Strategy" |
|
540 | + // todo: which would apply payments using the capitalist "first come first paid" approach |
|
541 | + // todo: then have another strategy class like "Distributed_Reg_Payment_Strategy" |
|
542 | + // todo: which would be the socialist "everybody gets a piece of pie" approach, |
|
543 | + // todo: which would be better for deposits, where you want a bit of the payment applied to each registration |
|
544 | + $refund = $payment->is_a_refund(); |
|
545 | + // how much is available to apply to registrations? |
|
546 | + $available_payment_amount = abs($payment->amount()); |
|
547 | + foreach ($registrations as $registration) { |
|
548 | + if ($registration instanceof EE_Registration) { |
|
549 | + // nothing left? |
|
550 | + if ($available_payment_amount <= 0) { |
|
551 | + break; |
|
552 | + } |
|
553 | + if ($refund) { |
|
554 | + $available_payment_amount = $this->process_registration_refund($registration, $payment, $available_payment_amount); |
|
555 | + } else { |
|
556 | + $available_payment_amount = $this->process_registration_payment($registration, $payment, $available_payment_amount); |
|
557 | + } |
|
558 | + } |
|
559 | + } |
|
560 | + if ($available_payment_amount > 0 && apply_filters('FHEE__EE_Payment_Processor__process_registration_payments__display_notifications', false)) { |
|
561 | + EE_Error::add_attention( |
|
562 | + sprintf( |
|
563 | + __('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).', |
|
564 | + 'event_espresso'), |
|
565 | + EEH_Template::format_currency($available_payment_amount), |
|
566 | + implode(', ', array_keys($registrations)), |
|
567 | + '<br/>', |
|
568 | + EEH_Template::format_currency($payment->amount()) |
|
569 | + ), |
|
570 | + __FILE__, __FUNCTION__, __LINE__ |
|
571 | + ); |
|
572 | + } |
|
573 | + } |
|
574 | + |
|
575 | + |
|
576 | + |
|
577 | + /** |
|
578 | + * update registration REG_paid field after successful payment and link registration with payment |
|
579 | + * |
|
580 | + * @param EE_Registration $registration |
|
581 | + * @param EE_Payment $payment |
|
582 | + * @param float $available_payment_amount |
|
583 | + * @return float |
|
584 | + * @throws \EE_Error |
|
585 | + */ |
|
586 | + public function process_registration_payment( |
|
587 | + EE_Registration $registration, |
|
588 | + EE_Payment $payment, |
|
589 | + $available_payment_amount = 0.00 |
|
590 | + ) { |
|
591 | + $owing = $registration->final_price() - $registration->paid(); |
|
592 | + if ($owing > 0) { |
|
593 | + // don't allow payment amount to exceed the available payment amount, OR the amount owing |
|
594 | + $payment_amount = min($available_payment_amount, $owing); |
|
595 | + // update $available_payment_amount |
|
596 | + $available_payment_amount -= $payment_amount; |
|
597 | + //calculate and set new REG_paid |
|
598 | + $registration->set_paid($registration->paid() + $payment_amount); |
|
599 | + // now save it |
|
600 | + $this->_apply_registration_payment($registration, $payment, $payment_amount); |
|
601 | + } |
|
602 | + return $available_payment_amount; |
|
603 | + } |
|
604 | + |
|
605 | + |
|
606 | + |
|
607 | + /** |
|
608 | + * update registration REG_paid field after successful payment and link registration with payment |
|
609 | + * |
|
610 | + * @param EE_Registration $registration |
|
611 | + * @param EE_Payment $payment |
|
612 | + * @param float $payment_amount |
|
613 | + * @return void |
|
614 | + * @throws \EE_Error |
|
615 | + */ |
|
616 | + protected function _apply_registration_payment( |
|
617 | + EE_Registration $registration, |
|
618 | + EE_Payment $payment, |
|
619 | + $payment_amount = 0.00 |
|
620 | + ) { |
|
621 | + // find any existing reg payment records for this registration and payment |
|
622 | + $existing_reg_payment = EEM_Registration_Payment::instance()->get_one( |
|
623 | + array(array('REG_ID' => $registration->ID(), 'PAY_ID' => $payment->ID())) |
|
624 | + ); |
|
625 | + // if existing registration payment exists |
|
626 | + if ($existing_reg_payment instanceof EE_Registration_Payment) { |
|
627 | + // then update that record |
|
628 | + $existing_reg_payment->set_amount($payment_amount); |
|
629 | + $existing_reg_payment->save(); |
|
630 | + } else { |
|
631 | + // or add new relation between registration and payment and set amount |
|
632 | + $registration->_add_relation_to($payment, 'Payment', array('RPY_amount' => $payment_amount)); |
|
633 | + // make it stick |
|
634 | + $registration->save(); |
|
635 | + } |
|
636 | + } |
|
637 | + |
|
638 | + |
|
639 | + |
|
640 | + /** |
|
641 | + * update registration REG_paid field after refund and link registration with payment |
|
642 | + * |
|
643 | + * @param EE_Registration $registration |
|
644 | + * @param EE_Payment $payment |
|
645 | + * @param float $available_refund_amount - IMPORTANT !!! SEND AVAILABLE REFUND AMOUNT AS A POSITIVE NUMBER |
|
646 | + * @return float |
|
647 | + * @throws \EE_Error |
|
648 | + */ |
|
649 | + public function process_registration_refund( |
|
650 | + EE_Registration $registration, |
|
651 | + EE_Payment $payment, |
|
652 | + $available_refund_amount = 0.00 |
|
653 | + ) { |
|
654 | + //EEH_Debug_Tools::printr( $payment->amount(), '$payment->amount()', __FILE__, __LINE__ ); |
|
655 | + if ($registration->paid() > 0) { |
|
656 | + // ensure $available_refund_amount is NOT negative |
|
657 | + $available_refund_amount = (float)abs($available_refund_amount); |
|
658 | + // don't allow refund amount to exceed the available payment amount, OR the amount paid |
|
659 | + $refund_amount = min($available_refund_amount, (float)$registration->paid()); |
|
660 | + // update $available_payment_amount |
|
661 | + $available_refund_amount -= $refund_amount; |
|
662 | + //calculate and set new REG_paid |
|
663 | + $registration->set_paid($registration->paid() - $refund_amount); |
|
664 | + // convert payment amount back to a negative value for storage in the db |
|
665 | + $refund_amount = (float)abs($refund_amount) * -1; |
|
666 | + // now save it |
|
667 | + $this->_apply_registration_payment($registration, $payment, $refund_amount); |
|
668 | + } |
|
669 | + return $available_refund_amount; |
|
670 | + } |
|
671 | + |
|
672 | + |
|
673 | + |
|
674 | + /** |
|
675 | + * Process payments and transaction after payment process completed. |
|
676 | + * ultimately this will send the TXN and payment details off so that notifications can be sent out. |
|
677 | + * if this request happens to be processing an IPN, |
|
678 | + * then we will also set the Payment Options Reg Step to completed, |
|
679 | + * and attempt to completely finalize the TXN if all of the other Reg Steps are completed as well. |
|
680 | + * |
|
681 | + * @param EE_Transaction $transaction |
|
682 | + * @param EE_Payment $payment |
|
683 | + * @param bool $IPN |
|
684 | + * @throws \EE_Error |
|
685 | + */ |
|
686 | + protected function _post_payment_processing(EE_Transaction $transaction, EE_Payment $payment, $IPN = false) |
|
687 | + { |
|
688 | + /** @type EE_Transaction_Processor $transaction_processor */ |
|
689 | + $transaction_processor = EE_Registry::instance()->load_class('Transaction_Processor'); |
|
690 | + // is the Payment Options Reg Step completed ? |
|
691 | + $payment_options_step_completed = $transaction->reg_step_completed('payment_options'); |
|
692 | + // if the Payment Options Reg Step is completed... |
|
693 | + $revisit = $payment_options_step_completed === true ? true : false; |
|
694 | + // then this is kinda sorta a revisit with regards to payments at least |
|
695 | + $transaction_processor->set_revisit($revisit); |
|
696 | + // if this is an IPN, let's consider the Payment Options Reg Step completed if not already |
|
697 | + if ( |
|
698 | + $IPN |
|
699 | + && $payment_options_step_completed !== true |
|
700 | + && ($payment->is_approved() || $payment->is_pending()) |
|
701 | + ) { |
|
702 | + $payment_options_step_completed = $transaction->set_reg_step_completed( |
|
703 | + 'payment_options' |
|
704 | + ); |
|
705 | + } |
|
706 | + // maybe update status, but don't save transaction just yet |
|
707 | + $transaction->update_status_based_on_total_paid(false); |
|
708 | + // check if 'finalize_registration' step has been completed... |
|
709 | + $finalized = $transaction->reg_step_completed('finalize_registration'); |
|
710 | + // if this is an IPN and the final step has not been initiated |
|
711 | + if ($IPN && $payment_options_step_completed && $finalized === false) { |
|
712 | + // and if it hasn't already been set as being started... |
|
713 | + $finalized = $transaction->set_reg_step_initiated('finalize_registration'); |
|
714 | + } |
|
715 | + $transaction->save(); |
|
716 | + // because the above will return false if the final step was not fully completed, we need to check again... |
|
717 | + if ($IPN && $finalized !== false) { |
|
718 | + // and if we are all good to go, then send out notifications |
|
719 | + add_filter('FHEE__EED_Messages___maybe_registration__deliver_notifications', '__return_true'); |
|
720 | + //ok, now process the transaction according to the payment |
|
721 | + $transaction_processor->update_transaction_and_registrations_after_checkout_or_payment($transaction, $payment); |
|
722 | + } |
|
723 | + // DEBUG LOG |
|
724 | + $payment_method = $payment->payment_method(); |
|
725 | + if ($payment_method instanceof EE_Payment_Method) { |
|
726 | + $payment_method_type_obj = $payment_method->type_obj(); |
|
727 | + if ($payment_method_type_obj instanceof EE_PMT_Base) { |
|
728 | + $gateway = $payment_method_type_obj->get_gateway(); |
|
729 | + if ($gateway instanceof EE_Gateway) { |
|
730 | + $gateway->log( |
|
731 | + array( |
|
732 | + 'message' => __('Post Payment Transaction Details', 'event_espresso'), |
|
733 | + 'transaction' => $transaction->model_field_array(), |
|
734 | + 'finalized' => $finalized, |
|
735 | + 'IPN' => $IPN, |
|
736 | + 'deliver_notifications' => has_filter( |
|
737 | + 'FHEE__EED_Messages___maybe_registration__deliver_notifications' |
|
738 | + ), |
|
739 | + ), |
|
740 | + $payment |
|
741 | + ); |
|
742 | + } |
|
743 | + } |
|
744 | + } |
|
745 | + } |
|
746 | + |
|
747 | + |
|
748 | + |
|
749 | + /** |
|
750 | + * Force posts to PayPal to use TLS v1.2. See: |
|
751 | + * https://core.trac.wordpress.org/ticket/36320 |
|
752 | + * https://core.trac.wordpress.org/ticket/34924#comment:15 |
|
753 | + * https://www.paypal-knowledge.com/infocenter/index?page=content&widgetview=true&id=FAQ1914&viewlocale=en_US |
|
754 | + * This will affect paypal standard, pro, express, and payflow. |
|
755 | + */ |
|
756 | + public static function _curl_requests_to_paypal_use_tls($handle, $r, $url) |
|
757 | + { |
|
758 | + if (strstr($url, 'https://') && strstr($url, '.paypal.com')) { |
|
759 | + //Use the value of the constant CURL_SSLVERSION_TLSv1 = 1 |
|
760 | + //instead of the constant because it might not be defined |
|
761 | + curl_setopt($handle, CURLOPT_SSLVERSION, 1); |
|
762 | + } |
|
763 | + } |
|
764 | 764 | } |
@@ -32,19 +32,19 @@ |
||
32 | 32 | * @return \EventEspresso\core\Psr4Autoloader |
33 | 33 | */ |
34 | 34 | public function initializeAutoloader() { |
35 | - static $initialized = false; |
|
36 | - if ( ! $initialized) { |
|
37 | - // instantiate PSR4 autoloader |
|
35 | + static $initialized = false; |
|
36 | + if ( ! $initialized) { |
|
37 | + // instantiate PSR4 autoloader |
|
38 | 38 | espresso_load_required( 'Psr4Autoloader', EE_CORE . 'Psr4Autoloader.php' ); |
39 | - EE_Psr4AutoloaderInit::$psr4_loader = new Psr4Autoloader(); |
|
40 | - // register the autoloader |
|
41 | - EE_Psr4AutoloaderInit::$psr4_loader->register(); |
|
42 | - // register the base directories for the namespace prefix |
|
43 | - EE_Psr4AutoloaderInit::$psr4_loader->addNamespace('EventEspresso', EE_PLUGIN_DIR_PATH); |
|
44 | - EE_Psr4AutoloaderInit::$psr4_loader->addNamespace('EventEspressoBatchRequest', EE_LIBRARIES . 'batch'); |
|
45 | - $initialized = true; |
|
46 | - } |
|
47 | - } |
|
39 | + EE_Psr4AutoloaderInit::$psr4_loader = new Psr4Autoloader(); |
|
40 | + // register the autoloader |
|
41 | + EE_Psr4AutoloaderInit::$psr4_loader->register(); |
|
42 | + // register the base directories for the namespace prefix |
|
43 | + EE_Psr4AutoloaderInit::$psr4_loader->addNamespace('EventEspresso', EE_PLUGIN_DIR_PATH); |
|
44 | + EE_Psr4AutoloaderInit::$psr4_loader->addNamespace('EventEspressoBatchRequest', EE_LIBRARIES . 'batch'); |
|
45 | + $initialized = true; |
|
46 | + } |
|
47 | + } |
|
48 | 48 | |
49 | 49 | |
50 | 50 |
@@ -35,13 +35,13 @@ |
||
35 | 35 | static $initialized = false; |
36 | 36 | if ( ! $initialized) { |
37 | 37 | // instantiate PSR4 autoloader |
38 | - espresso_load_required( 'Psr4Autoloader', EE_CORE . 'Psr4Autoloader.php' ); |
|
38 | + espresso_load_required('Psr4Autoloader', EE_CORE.'Psr4Autoloader.php'); |
|
39 | 39 | EE_Psr4AutoloaderInit::$psr4_loader = new Psr4Autoloader(); |
40 | 40 | // register the autoloader |
41 | 41 | EE_Psr4AutoloaderInit::$psr4_loader->register(); |
42 | 42 | // register the base directories for the namespace prefix |
43 | 43 | EE_Psr4AutoloaderInit::$psr4_loader->addNamespace('EventEspresso', EE_PLUGIN_DIR_PATH); |
44 | - EE_Psr4AutoloaderInit::$psr4_loader->addNamespace('EventEspressoBatchRequest', EE_LIBRARIES . 'batch'); |
|
44 | + EE_Psr4AutoloaderInit::$psr4_loader->addNamespace('EventEspressoBatchRequest', EE_LIBRARIES.'batch'); |
|
45 | 45 | $initialized = true; |
46 | 46 | } |
47 | 47 | } |
@@ -5,8 +5,8 @@ discard block |
||
5 | 5 | // if you're a dev and want to receive all errors via email |
6 | 6 | // add this to your wp-config.php: define( 'EE_ERROR_EMAILS', TRUE ); |
7 | 7 | if (defined('WP_DEBUG') && WP_DEBUG === true && defined('EE_ERROR_EMAILS') && EE_ERROR_EMAILS === true) { |
8 | - set_error_handler(array('EE_Error', 'error_handler')); |
|
9 | - register_shutdown_function(array('EE_Error', 'fatal_error_handler')); |
|
8 | + set_error_handler(array('EE_Error', 'error_handler')); |
|
9 | + register_shutdown_function(array('EE_Error', 'fatal_error_handler')); |
|
10 | 10 | } |
11 | 11 | |
12 | 12 | |
@@ -23,257 +23,257 @@ discard block |
||
23 | 23 | { |
24 | 24 | |
25 | 25 | |
26 | - /** |
|
27 | - * name of the file to log exceptions to |
|
28 | - * |
|
29 | - * @var string |
|
30 | - */ |
|
31 | - private static $_exception_log_file = 'espresso_error_log.txt'; |
|
32 | - |
|
33 | - /** |
|
34 | - * stores details for all exception |
|
35 | - * |
|
36 | - * @var array |
|
37 | - */ |
|
38 | - private static $_all_exceptions = array(); |
|
39 | - |
|
40 | - /** |
|
41 | - * tracks number of errors |
|
42 | - * |
|
43 | - * @var int |
|
44 | - */ |
|
45 | - private static $_error_count = 0; |
|
46 | - |
|
47 | - /** |
|
48 | - * @var array $_espresso_notices |
|
49 | - */ |
|
50 | - private static $_espresso_notices = array('success' => false, 'errors' => false, 'attention' => false); |
|
51 | - |
|
52 | - |
|
53 | - |
|
54 | - /** |
|
55 | - * @override default exception handling |
|
56 | - * @param string $message |
|
57 | - * @param int $code |
|
58 | - * @param Exception|null $previous |
|
59 | - */ |
|
60 | - public function __construct($message, $code = 0, Exception $previous = null) |
|
61 | - { |
|
62 | - if (version_compare(PHP_VERSION, '5.3.0', '<')) { |
|
63 | - parent::__construct($message, $code); |
|
64 | - } else { |
|
65 | - parent::__construct($message, $code, $previous); |
|
66 | - } |
|
67 | - } |
|
68 | - |
|
69 | - |
|
70 | - |
|
71 | - /** |
|
72 | - * error_handler |
|
73 | - * |
|
74 | - * @param $code |
|
75 | - * @param $message |
|
76 | - * @param $file |
|
77 | - * @param $line |
|
78 | - * @return void |
|
79 | - */ |
|
80 | - public static function error_handler($code, $message, $file, $line) |
|
81 | - { |
|
82 | - $type = EE_Error::error_type($code); |
|
83 | - $site = site_url(); |
|
84 | - switch ($site) { |
|
85 | - case 'http://ee4.eventespresso.com/' : |
|
86 | - case 'http://ee4decaf.eventespresso.com/' : |
|
87 | - case 'http://ee4hf.eventespresso.com/' : |
|
88 | - case 'http://ee4a.eventespresso.com/' : |
|
89 | - case 'http://ee4ad.eventespresso.com/' : |
|
90 | - case 'http://ee4b.eventespresso.com/' : |
|
91 | - case 'http://ee4bd.eventespresso.com/' : |
|
92 | - case 'http://ee4d.eventespresso.com/' : |
|
93 | - case 'http://ee4dd.eventespresso.com/' : |
|
94 | - $to = '[email protected]'; |
|
95 | - break; |
|
96 | - default : |
|
97 | - $to = get_option('admin_email'); |
|
98 | - } |
|
99 | - $subject = $type . ' ' . $message . ' in ' . EVENT_ESPRESSO_VERSION . ' on ' . site_url(); |
|
100 | - $msg = EE_Error::_format_error($type, $message, $file, $line); |
|
101 | - if (function_exists('wp_mail')) { |
|
102 | - add_filter('wp_mail_content_type', array('EE_Error', 'set_content_type')); |
|
103 | - wp_mail($to, $subject, $msg); |
|
104 | - } |
|
105 | - echo '<div id="message" class="espresso-notices error"><p>'; |
|
106 | - echo $type . ': ' . $message . '<br />' . $file . ' line ' . $line; |
|
107 | - echo '<br /></p></div>'; |
|
108 | - } |
|
109 | - |
|
110 | - |
|
111 | - |
|
112 | - /** |
|
113 | - * error_type |
|
114 | - * http://www.php.net/manual/en/errorfunc.constants.php#109430 |
|
115 | - * |
|
116 | - * @param $code |
|
117 | - * @return string |
|
118 | - */ |
|
119 | - public static function error_type($code) |
|
120 | - { |
|
121 | - switch ($code) { |
|
122 | - case E_ERROR: // 1 // |
|
123 | - return 'E_ERROR'; |
|
124 | - case E_WARNING: // 2 // |
|
125 | - return 'E_WARNING'; |
|
126 | - case E_PARSE: // 4 // |
|
127 | - return 'E_PARSE'; |
|
128 | - case E_NOTICE: // 8 // |
|
129 | - return 'E_NOTICE'; |
|
130 | - case E_CORE_ERROR: // 16 // |
|
131 | - return 'E_CORE_ERROR'; |
|
132 | - case E_CORE_WARNING: // 32 // |
|
133 | - return 'E_CORE_WARNING'; |
|
134 | - case E_COMPILE_ERROR: // 64 // |
|
135 | - return 'E_COMPILE_ERROR'; |
|
136 | - case E_COMPILE_WARNING: // 128 // |
|
137 | - return 'E_COMPILE_WARNING'; |
|
138 | - case E_USER_ERROR: // 256 // |
|
139 | - return 'E_USER_ERROR'; |
|
140 | - case E_USER_WARNING: // 512 // |
|
141 | - return 'E_USER_WARNING'; |
|
142 | - case E_USER_NOTICE: // 1024 // |
|
143 | - return 'E_USER_NOTICE'; |
|
144 | - case E_STRICT: // 2048 // |
|
145 | - return 'E_STRICT'; |
|
146 | - case E_RECOVERABLE_ERROR: // 4096 // |
|
147 | - return 'E_RECOVERABLE_ERROR'; |
|
148 | - case E_DEPRECATED: // 8192 // |
|
149 | - return 'E_DEPRECATED'; |
|
150 | - case E_USER_DEPRECATED: // 16384 // |
|
151 | - return 'E_USER_DEPRECATED'; |
|
152 | - case E_ALL: // 16384 // |
|
153 | - return 'E_ALL'; |
|
154 | - } |
|
155 | - return ''; |
|
156 | - } |
|
157 | - |
|
158 | - |
|
159 | - |
|
160 | - /** |
|
161 | - * fatal_error_handler |
|
162 | - * |
|
163 | - * @return void |
|
164 | - */ |
|
165 | - public static function fatal_error_handler() |
|
166 | - { |
|
167 | - $last_error = error_get_last(); |
|
168 | - if ($last_error['type'] === E_ERROR) { |
|
169 | - EE_Error::error_handler(E_ERROR, $last_error['message'], $last_error['file'], $last_error['line']); |
|
170 | - } |
|
171 | - } |
|
172 | - |
|
173 | - |
|
174 | - |
|
175 | - /** |
|
176 | - * _format_error |
|
177 | - * |
|
178 | - * @param $code |
|
179 | - * @param $message |
|
180 | - * @param $file |
|
181 | - * @param $line |
|
182 | - * @return string |
|
183 | - */ |
|
184 | - private static function _format_error($code, $message, $file, $line) |
|
185 | - { |
|
186 | - $html = "<table cellpadding='5'><thead bgcolor='#f8f8f8'><th>Item</th><th align='left'>Details</th></thead><tbody>"; |
|
187 | - $html .= "<tr valign='top'><td><b>Code</b></td><td>$code</td></tr>"; |
|
188 | - $html .= "<tr valign='top'><td><b>Error</b></td><td>$message</td></tr>"; |
|
189 | - $html .= "<tr valign='top'><td><b>File</b></td><td>$file</td></tr>"; |
|
190 | - $html .= "<tr valign='top'><td><b>Line</b></td><td>$line</td></tr>"; |
|
191 | - $html .= '</tbody></table>'; |
|
192 | - return $html; |
|
193 | - } |
|
194 | - |
|
195 | - |
|
196 | - |
|
197 | - /** |
|
198 | - * set_content_type |
|
199 | - * |
|
200 | - * @param $content_type |
|
201 | - * @return string |
|
202 | - */ |
|
203 | - public static function set_content_type($content_type) |
|
204 | - { |
|
205 | - return 'text/html'; |
|
206 | - } |
|
207 | - |
|
208 | - |
|
209 | - |
|
210 | - /** |
|
211 | - * @return void |
|
212 | - * @throws EE_Error |
|
213 | - * @throws ReflectionException |
|
214 | - */ |
|
215 | - public function get_error() |
|
216 | - { |
|
217 | - if (apply_filters('FHEE__EE_Error__get_error__show_normal_exceptions', false)) { |
|
218 | - throw $this; |
|
219 | - } |
|
220 | - // get separate user and developer messages if they exist |
|
221 | - $msg = explode('||', $this->getMessage()); |
|
222 | - $user_msg = $msg[0]; |
|
223 | - $dev_msg = isset($msg[1]) ? $msg[1] : $msg[0]; |
|
224 | - $msg = WP_DEBUG ? $dev_msg : $user_msg; |
|
225 | - // add details to _all_exceptions array |
|
226 | - $x_time = time(); |
|
227 | - self::$_all_exceptions[$x_time]['name'] = get_class($this); |
|
228 | - self::$_all_exceptions[$x_time]['file'] = $this->getFile(); |
|
229 | - self::$_all_exceptions[$x_time]['line'] = $this->getLine(); |
|
230 | - self::$_all_exceptions[$x_time]['msg'] = $msg; |
|
231 | - self::$_all_exceptions[$x_time]['code'] = $this->getCode(); |
|
232 | - self::$_all_exceptions[$x_time]['trace'] = $this->getTrace(); |
|
233 | - self::$_all_exceptions[$x_time]['string'] = $this->getTraceAsString(); |
|
234 | - self::$_error_count++; |
|
235 | - //add_action( 'shutdown', array( $this, 'display_errors' )); |
|
236 | - $this->display_errors(); |
|
237 | - } |
|
238 | - |
|
239 | - |
|
240 | - |
|
241 | - /** |
|
242 | - * has_error |
|
243 | - * |
|
244 | - * @param bool $check_stored |
|
245 | - * @param string $type_to_check |
|
246 | - * @return bool |
|
247 | - */ |
|
248 | - public static function has_error($check_stored = false, $type_to_check = 'errors') |
|
249 | - { |
|
250 | - $has_error = isset(self::$_espresso_notices[$type_to_check]) |
|
251 | - && ! empty(self::$_espresso_notices[$type_to_check]) |
|
252 | - ? true |
|
253 | - : false; |
|
254 | - if ($check_stored && ! $has_error) { |
|
255 | - $notices = (array)get_option('ee_notices', array()); |
|
256 | - foreach ($notices as $type => $notice) { |
|
257 | - if ($type === $type_to_check && $notice) { |
|
258 | - return true; |
|
259 | - } |
|
260 | - } |
|
261 | - } |
|
262 | - return $has_error; |
|
263 | - } |
|
264 | - |
|
265 | - |
|
266 | - |
|
267 | - /** |
|
268 | - * display_errors |
|
269 | - * |
|
270 | - * @echo string |
|
271 | - * @throws \ReflectionException |
|
272 | - */ |
|
273 | - public function display_errors() |
|
274 | - { |
|
275 | - $trace_details = ''; |
|
276 | - $output = ' |
|
26 | + /** |
|
27 | + * name of the file to log exceptions to |
|
28 | + * |
|
29 | + * @var string |
|
30 | + */ |
|
31 | + private static $_exception_log_file = 'espresso_error_log.txt'; |
|
32 | + |
|
33 | + /** |
|
34 | + * stores details for all exception |
|
35 | + * |
|
36 | + * @var array |
|
37 | + */ |
|
38 | + private static $_all_exceptions = array(); |
|
39 | + |
|
40 | + /** |
|
41 | + * tracks number of errors |
|
42 | + * |
|
43 | + * @var int |
|
44 | + */ |
|
45 | + private static $_error_count = 0; |
|
46 | + |
|
47 | + /** |
|
48 | + * @var array $_espresso_notices |
|
49 | + */ |
|
50 | + private static $_espresso_notices = array('success' => false, 'errors' => false, 'attention' => false); |
|
51 | + |
|
52 | + |
|
53 | + |
|
54 | + /** |
|
55 | + * @override default exception handling |
|
56 | + * @param string $message |
|
57 | + * @param int $code |
|
58 | + * @param Exception|null $previous |
|
59 | + */ |
|
60 | + public function __construct($message, $code = 0, Exception $previous = null) |
|
61 | + { |
|
62 | + if (version_compare(PHP_VERSION, '5.3.0', '<')) { |
|
63 | + parent::__construct($message, $code); |
|
64 | + } else { |
|
65 | + parent::__construct($message, $code, $previous); |
|
66 | + } |
|
67 | + } |
|
68 | + |
|
69 | + |
|
70 | + |
|
71 | + /** |
|
72 | + * error_handler |
|
73 | + * |
|
74 | + * @param $code |
|
75 | + * @param $message |
|
76 | + * @param $file |
|
77 | + * @param $line |
|
78 | + * @return void |
|
79 | + */ |
|
80 | + public static function error_handler($code, $message, $file, $line) |
|
81 | + { |
|
82 | + $type = EE_Error::error_type($code); |
|
83 | + $site = site_url(); |
|
84 | + switch ($site) { |
|
85 | + case 'http://ee4.eventespresso.com/' : |
|
86 | + case 'http://ee4decaf.eventespresso.com/' : |
|
87 | + case 'http://ee4hf.eventespresso.com/' : |
|
88 | + case 'http://ee4a.eventespresso.com/' : |
|
89 | + case 'http://ee4ad.eventespresso.com/' : |
|
90 | + case 'http://ee4b.eventespresso.com/' : |
|
91 | + case 'http://ee4bd.eventespresso.com/' : |
|
92 | + case 'http://ee4d.eventespresso.com/' : |
|
93 | + case 'http://ee4dd.eventespresso.com/' : |
|
94 | + $to = '[email protected]'; |
|
95 | + break; |
|
96 | + default : |
|
97 | + $to = get_option('admin_email'); |
|
98 | + } |
|
99 | + $subject = $type . ' ' . $message . ' in ' . EVENT_ESPRESSO_VERSION . ' on ' . site_url(); |
|
100 | + $msg = EE_Error::_format_error($type, $message, $file, $line); |
|
101 | + if (function_exists('wp_mail')) { |
|
102 | + add_filter('wp_mail_content_type', array('EE_Error', 'set_content_type')); |
|
103 | + wp_mail($to, $subject, $msg); |
|
104 | + } |
|
105 | + echo '<div id="message" class="espresso-notices error"><p>'; |
|
106 | + echo $type . ': ' . $message . '<br />' . $file . ' line ' . $line; |
|
107 | + echo '<br /></p></div>'; |
|
108 | + } |
|
109 | + |
|
110 | + |
|
111 | + |
|
112 | + /** |
|
113 | + * error_type |
|
114 | + * http://www.php.net/manual/en/errorfunc.constants.php#109430 |
|
115 | + * |
|
116 | + * @param $code |
|
117 | + * @return string |
|
118 | + */ |
|
119 | + public static function error_type($code) |
|
120 | + { |
|
121 | + switch ($code) { |
|
122 | + case E_ERROR: // 1 // |
|
123 | + return 'E_ERROR'; |
|
124 | + case E_WARNING: // 2 // |
|
125 | + return 'E_WARNING'; |
|
126 | + case E_PARSE: // 4 // |
|
127 | + return 'E_PARSE'; |
|
128 | + case E_NOTICE: // 8 // |
|
129 | + return 'E_NOTICE'; |
|
130 | + case E_CORE_ERROR: // 16 // |
|
131 | + return 'E_CORE_ERROR'; |
|
132 | + case E_CORE_WARNING: // 32 // |
|
133 | + return 'E_CORE_WARNING'; |
|
134 | + case E_COMPILE_ERROR: // 64 // |
|
135 | + return 'E_COMPILE_ERROR'; |
|
136 | + case E_COMPILE_WARNING: // 128 // |
|
137 | + return 'E_COMPILE_WARNING'; |
|
138 | + case E_USER_ERROR: // 256 // |
|
139 | + return 'E_USER_ERROR'; |
|
140 | + case E_USER_WARNING: // 512 // |
|
141 | + return 'E_USER_WARNING'; |
|
142 | + case E_USER_NOTICE: // 1024 // |
|
143 | + return 'E_USER_NOTICE'; |
|
144 | + case E_STRICT: // 2048 // |
|
145 | + return 'E_STRICT'; |
|
146 | + case E_RECOVERABLE_ERROR: // 4096 // |
|
147 | + return 'E_RECOVERABLE_ERROR'; |
|
148 | + case E_DEPRECATED: // 8192 // |
|
149 | + return 'E_DEPRECATED'; |
|
150 | + case E_USER_DEPRECATED: // 16384 // |
|
151 | + return 'E_USER_DEPRECATED'; |
|
152 | + case E_ALL: // 16384 // |
|
153 | + return 'E_ALL'; |
|
154 | + } |
|
155 | + return ''; |
|
156 | + } |
|
157 | + |
|
158 | + |
|
159 | + |
|
160 | + /** |
|
161 | + * fatal_error_handler |
|
162 | + * |
|
163 | + * @return void |
|
164 | + */ |
|
165 | + public static function fatal_error_handler() |
|
166 | + { |
|
167 | + $last_error = error_get_last(); |
|
168 | + if ($last_error['type'] === E_ERROR) { |
|
169 | + EE_Error::error_handler(E_ERROR, $last_error['message'], $last_error['file'], $last_error['line']); |
|
170 | + } |
|
171 | + } |
|
172 | + |
|
173 | + |
|
174 | + |
|
175 | + /** |
|
176 | + * _format_error |
|
177 | + * |
|
178 | + * @param $code |
|
179 | + * @param $message |
|
180 | + * @param $file |
|
181 | + * @param $line |
|
182 | + * @return string |
|
183 | + */ |
|
184 | + private static function _format_error($code, $message, $file, $line) |
|
185 | + { |
|
186 | + $html = "<table cellpadding='5'><thead bgcolor='#f8f8f8'><th>Item</th><th align='left'>Details</th></thead><tbody>"; |
|
187 | + $html .= "<tr valign='top'><td><b>Code</b></td><td>$code</td></tr>"; |
|
188 | + $html .= "<tr valign='top'><td><b>Error</b></td><td>$message</td></tr>"; |
|
189 | + $html .= "<tr valign='top'><td><b>File</b></td><td>$file</td></tr>"; |
|
190 | + $html .= "<tr valign='top'><td><b>Line</b></td><td>$line</td></tr>"; |
|
191 | + $html .= '</tbody></table>'; |
|
192 | + return $html; |
|
193 | + } |
|
194 | + |
|
195 | + |
|
196 | + |
|
197 | + /** |
|
198 | + * set_content_type |
|
199 | + * |
|
200 | + * @param $content_type |
|
201 | + * @return string |
|
202 | + */ |
|
203 | + public static function set_content_type($content_type) |
|
204 | + { |
|
205 | + return 'text/html'; |
|
206 | + } |
|
207 | + |
|
208 | + |
|
209 | + |
|
210 | + /** |
|
211 | + * @return void |
|
212 | + * @throws EE_Error |
|
213 | + * @throws ReflectionException |
|
214 | + */ |
|
215 | + public function get_error() |
|
216 | + { |
|
217 | + if (apply_filters('FHEE__EE_Error__get_error__show_normal_exceptions', false)) { |
|
218 | + throw $this; |
|
219 | + } |
|
220 | + // get separate user and developer messages if they exist |
|
221 | + $msg = explode('||', $this->getMessage()); |
|
222 | + $user_msg = $msg[0]; |
|
223 | + $dev_msg = isset($msg[1]) ? $msg[1] : $msg[0]; |
|
224 | + $msg = WP_DEBUG ? $dev_msg : $user_msg; |
|
225 | + // add details to _all_exceptions array |
|
226 | + $x_time = time(); |
|
227 | + self::$_all_exceptions[$x_time]['name'] = get_class($this); |
|
228 | + self::$_all_exceptions[$x_time]['file'] = $this->getFile(); |
|
229 | + self::$_all_exceptions[$x_time]['line'] = $this->getLine(); |
|
230 | + self::$_all_exceptions[$x_time]['msg'] = $msg; |
|
231 | + self::$_all_exceptions[$x_time]['code'] = $this->getCode(); |
|
232 | + self::$_all_exceptions[$x_time]['trace'] = $this->getTrace(); |
|
233 | + self::$_all_exceptions[$x_time]['string'] = $this->getTraceAsString(); |
|
234 | + self::$_error_count++; |
|
235 | + //add_action( 'shutdown', array( $this, 'display_errors' )); |
|
236 | + $this->display_errors(); |
|
237 | + } |
|
238 | + |
|
239 | + |
|
240 | + |
|
241 | + /** |
|
242 | + * has_error |
|
243 | + * |
|
244 | + * @param bool $check_stored |
|
245 | + * @param string $type_to_check |
|
246 | + * @return bool |
|
247 | + */ |
|
248 | + public static function has_error($check_stored = false, $type_to_check = 'errors') |
|
249 | + { |
|
250 | + $has_error = isset(self::$_espresso_notices[$type_to_check]) |
|
251 | + && ! empty(self::$_espresso_notices[$type_to_check]) |
|
252 | + ? true |
|
253 | + : false; |
|
254 | + if ($check_stored && ! $has_error) { |
|
255 | + $notices = (array)get_option('ee_notices', array()); |
|
256 | + foreach ($notices as $type => $notice) { |
|
257 | + if ($type === $type_to_check && $notice) { |
|
258 | + return true; |
|
259 | + } |
|
260 | + } |
|
261 | + } |
|
262 | + return $has_error; |
|
263 | + } |
|
264 | + |
|
265 | + |
|
266 | + |
|
267 | + /** |
|
268 | + * display_errors |
|
269 | + * |
|
270 | + * @echo string |
|
271 | + * @throws \ReflectionException |
|
272 | + */ |
|
273 | + public function display_errors() |
|
274 | + { |
|
275 | + $trace_details = ''; |
|
276 | + $output = ' |
|
277 | 277 | <style type="text/css"> |
278 | 278 | #ee-error-message { |
279 | 279 | max-width:90% !important; |
@@ -329,21 +329,21 @@ discard block |
||
329 | 329 | } |
330 | 330 | </style> |
331 | 331 | <div id="ee-error-message" class="error">'; |
332 | - if (! WP_DEBUG) { |
|
333 | - $output .= ' |
|
332 | + if (! WP_DEBUG) { |
|
333 | + $output .= ' |
|
334 | 334 | <p>'; |
335 | - } |
|
336 | - // cycle thru errors |
|
337 | - foreach (self::$_all_exceptions as $time => $ex) { |
|
338 | - $error_code = ''; |
|
339 | - // process trace info |
|
340 | - if (empty($ex['trace'])) { |
|
341 | - $trace_details .= __( |
|
342 | - 'Sorry, but no trace information was available for this exception.', |
|
343 | - 'event_espresso' |
|
344 | - ); |
|
345 | - } else { |
|
346 | - $trace_details .= ' |
|
335 | + } |
|
336 | + // cycle thru errors |
|
337 | + foreach (self::$_all_exceptions as $time => $ex) { |
|
338 | + $error_code = ''; |
|
339 | + // process trace info |
|
340 | + if (empty($ex['trace'])) { |
|
341 | + $trace_details .= __( |
|
342 | + 'Sorry, but no trace information was available for this exception.', |
|
343 | + 'event_espresso' |
|
344 | + ); |
|
345 | + } else { |
|
346 | + $trace_details .= ' |
|
347 | 347 | <div id="ee-trace-details"> |
348 | 348 | <table width="100%" border="0" cellpadding="5" cellspacing="0"> |
349 | 349 | <tr> |
@@ -353,38 +353,38 @@ discard block |
||
353 | 353 | <th scope="col" align="left">Class</th> |
354 | 354 | <th scope="col" align="left">Method( arguments )</th> |
355 | 355 | </tr>'; |
356 | - $last_on_stack = count($ex['trace']) - 1; |
|
357 | - // reverse array so that stack is in proper chronological order |
|
358 | - $sorted_trace = array_reverse($ex['trace']); |
|
359 | - foreach ($sorted_trace as $nmbr => $trace) { |
|
360 | - $file = isset($trace['file']) ? $trace['file'] : ''; |
|
361 | - $class = isset($trace['class']) ? $trace['class'] : ''; |
|
362 | - $type = isset($trace['type']) ? $trace['type'] : ''; |
|
363 | - $function = isset($trace['function']) ? $trace['function'] : ''; |
|
364 | - $args = isset($trace['args']) ? $this->_convert_args_to_string($trace['args']) : ''; |
|
365 | - $line = isset($trace['line']) ? $trace['line'] : ''; |
|
366 | - $zebra = ($nmbr % 2) ? ' odd' : ''; |
|
367 | - if (empty($file) && ! empty($class)) { |
|
368 | - $a = new ReflectionClass($class); |
|
369 | - $file = $a->getFileName(); |
|
370 | - if (empty($line) && ! empty($function)) { |
|
371 | - $b = new ReflectionMethod($class, $function); |
|
372 | - $line = $b->getStartLine(); |
|
373 | - } |
|
374 | - } |
|
375 | - if ($nmbr === $last_on_stack) { |
|
376 | - $file = $ex['file'] !== '' ? $ex['file'] : $file; |
|
377 | - $line = $ex['line'] !== '' ? $ex['line'] : $line; |
|
378 | - $error_code = self::generate_error_code($file, $trace['function'], $line); |
|
379 | - } |
|
380 | - $nmbr_dsply = ! empty($nmbr) ? $nmbr : ' '; |
|
381 | - $line_dsply = ! empty($line) ? $line : ' '; |
|
382 | - $file_dsply = ! empty($file) ? $file : ' '; |
|
383 | - $class_dsply = ! empty($class) ? $class : ' '; |
|
384 | - $type_dsply = ! empty($type) ? $type : ' '; |
|
385 | - $function_dsply = ! empty($function) ? $function : ' '; |
|
386 | - $args_dsply = ! empty($args) ? '( ' . $args . ' )' : ''; |
|
387 | - $trace_details .= ' |
|
356 | + $last_on_stack = count($ex['trace']) - 1; |
|
357 | + // reverse array so that stack is in proper chronological order |
|
358 | + $sorted_trace = array_reverse($ex['trace']); |
|
359 | + foreach ($sorted_trace as $nmbr => $trace) { |
|
360 | + $file = isset($trace['file']) ? $trace['file'] : ''; |
|
361 | + $class = isset($trace['class']) ? $trace['class'] : ''; |
|
362 | + $type = isset($trace['type']) ? $trace['type'] : ''; |
|
363 | + $function = isset($trace['function']) ? $trace['function'] : ''; |
|
364 | + $args = isset($trace['args']) ? $this->_convert_args_to_string($trace['args']) : ''; |
|
365 | + $line = isset($trace['line']) ? $trace['line'] : ''; |
|
366 | + $zebra = ($nmbr % 2) ? ' odd' : ''; |
|
367 | + if (empty($file) && ! empty($class)) { |
|
368 | + $a = new ReflectionClass($class); |
|
369 | + $file = $a->getFileName(); |
|
370 | + if (empty($line) && ! empty($function)) { |
|
371 | + $b = new ReflectionMethod($class, $function); |
|
372 | + $line = $b->getStartLine(); |
|
373 | + } |
|
374 | + } |
|
375 | + if ($nmbr === $last_on_stack) { |
|
376 | + $file = $ex['file'] !== '' ? $ex['file'] : $file; |
|
377 | + $line = $ex['line'] !== '' ? $ex['line'] : $line; |
|
378 | + $error_code = self::generate_error_code($file, $trace['function'], $line); |
|
379 | + } |
|
380 | + $nmbr_dsply = ! empty($nmbr) ? $nmbr : ' '; |
|
381 | + $line_dsply = ! empty($line) ? $line : ' '; |
|
382 | + $file_dsply = ! empty($file) ? $file : ' '; |
|
383 | + $class_dsply = ! empty($class) ? $class : ' '; |
|
384 | + $type_dsply = ! empty($type) ? $type : ' '; |
|
385 | + $function_dsply = ! empty($function) ? $function : ' '; |
|
386 | + $args_dsply = ! empty($args) ? '( ' . $args . ' )' : ''; |
|
387 | + $trace_details .= ' |
|
388 | 388 | <tr> |
389 | 389 | <td align="right" class="' . $zebra . '">' . $nmbr_dsply . '</td> |
390 | 390 | <td align="right" class="' . $zebra . '">' . $line_dsply . '</td> |
@@ -392,684 +392,684 @@ discard block |
||
392 | 392 | <td align="left" class="' . $zebra . '">' . $class_dsply . '</td> |
393 | 393 | <td align="left" class="' . $zebra . '">' . $type_dsply . $function_dsply . $args_dsply . '</td> |
394 | 394 | </tr>'; |
395 | - } |
|
396 | - $trace_details .= ' |
|
395 | + } |
|
396 | + $trace_details .= ' |
|
397 | 397 | </table> |
398 | 398 | </div>'; |
399 | - } |
|
400 | - $ex['code'] = $ex['code'] ? $ex['code'] : $error_code; |
|
401 | - // add generic non-identifying messages for non-privileged users |
|
402 | - if (! WP_DEBUG) { |
|
403 | - $output .= '<span class="ee-error-user-msg-spn">' |
|
404 | - . trim($ex['msg']) |
|
405 | - . '</span> <sup>' |
|
406 | - . $ex['code'] |
|
407 | - . '</sup><br />'; |
|
408 | - } else { |
|
409 | - // or helpful developer messages if debugging is on |
|
410 | - $output .= ' |
|
399 | + } |
|
400 | + $ex['code'] = $ex['code'] ? $ex['code'] : $error_code; |
|
401 | + // add generic non-identifying messages for non-privileged users |
|
402 | + if (! WP_DEBUG) { |
|
403 | + $output .= '<span class="ee-error-user-msg-spn">' |
|
404 | + . trim($ex['msg']) |
|
405 | + . '</span> <sup>' |
|
406 | + . $ex['code'] |
|
407 | + . '</sup><br />'; |
|
408 | + } else { |
|
409 | + // or helpful developer messages if debugging is on |
|
410 | + $output .= ' |
|
411 | 411 | <div class="ee-error-dev-msg-dv"> |
412 | 412 | <p class="ee-error-dev-msg-pg"> |
413 | 413 | <strong class="ee-error-dev-msg-str">An ' |
414 | - . $ex['name'] |
|
415 | - . ' exception was thrown!</strong> <span>code: ' |
|
416 | - . $ex['code'] |
|
417 | - . '</span><br /> |
|
414 | + . $ex['name'] |
|
415 | + . ' exception was thrown!</strong> <span>code: ' |
|
416 | + . $ex['code'] |
|
417 | + . '</span><br /> |
|
418 | 418 | <span class="big-text">"' |
419 | - . trim($ex['msg']) |
|
420 | - . '"</span><br/> |
|
419 | + . trim($ex['msg']) |
|
420 | + . '"</span><br/> |
|
421 | 421 | <a id="display-ee-error-trace-' |
422 | - . self::$_error_count |
|
423 | - . $time |
|
424 | - . '" class="display-ee-error-trace-lnk small-text" rel="ee-error-trace-' |
|
425 | - . self::$_error_count |
|
426 | - . $time |
|
427 | - . '"> |
|
422 | + . self::$_error_count |
|
423 | + . $time |
|
424 | + . '" class="display-ee-error-trace-lnk small-text" rel="ee-error-trace-' |
|
425 | + . self::$_error_count |
|
426 | + . $time |
|
427 | + . '"> |
|
428 | 428 | ' |
429 | - . __('click to view backtrace and class/method details', 'event_espresso') |
|
430 | - . ' |
|
429 | + . __('click to view backtrace and class/method details', 'event_espresso') |
|
430 | + . ' |
|
431 | 431 | </a><br /> |
432 | 432 | <span class="small-text lt-grey-text">' |
433 | - . $ex['file'] |
|
434 | - . ' ( line no: ' |
|
435 | - . $ex['line'] |
|
436 | - . ' )</span> |
|
433 | + . $ex['file'] |
|
434 | + . ' ( line no: ' |
|
435 | + . $ex['line'] |
|
436 | + . ' )</span> |
|
437 | 437 | </p> |
438 | 438 | <div id="ee-error-trace-' |
439 | - . self::$_error_count |
|
440 | - . $time |
|
441 | - . '-dv" class="ee-error-trace-dv" style="display: none;"> |
|
439 | + . self::$_error_count |
|
440 | + . $time |
|
441 | + . '-dv" class="ee-error-trace-dv" style="display: none;"> |
|
442 | 442 | ' |
443 | - . $trace_details; |
|
444 | - if (! empty($class)) { |
|
445 | - $output .= ' |
|
443 | + . $trace_details; |
|
444 | + if (! empty($class)) { |
|
445 | + $output .= ' |
|
446 | 446 | <div style="padding:3px; margin:0 0 1em; border:1px solid #666; background:#fff; border-radius:3px;"> |
447 | 447 | <div style="padding:1em 2em; border:1px solid #666; background:#f9f9f9;"> |
448 | 448 | <h3>Class Details</h3>'; |
449 | - $a = new ReflectionClass($class); |
|
450 | - $output .= ' |
|
449 | + $a = new ReflectionClass($class); |
|
450 | + $output .= ' |
|
451 | 451 | <pre>' . $a . '</pre> |
452 | 452 | </div> |
453 | 453 | </div>'; |
454 | - } |
|
455 | - $output .= ' |
|
454 | + } |
|
455 | + $output .= ' |
|
456 | 456 | </div> |
457 | 457 | </div> |
458 | 458 | <br />'; |
459 | - } |
|
460 | - $this->write_to_error_log($time, $ex); |
|
461 | - } |
|
462 | - // remove last linebreak |
|
463 | - $output = substr($output, 0, -6); |
|
464 | - if (! WP_DEBUG) { |
|
465 | - $output .= ' |
|
459 | + } |
|
460 | + $this->write_to_error_log($time, $ex); |
|
461 | + } |
|
462 | + // remove last linebreak |
|
463 | + $output = substr($output, 0, -6); |
|
464 | + if (! WP_DEBUG) { |
|
465 | + $output .= ' |
|
466 | 466 | </p>'; |
467 | - } |
|
468 | - $output .= ' |
|
467 | + } |
|
468 | + $output .= ' |
|
469 | 469 | </div>'; |
470 | - $output .= self::_print_scripts(true); |
|
471 | - if (defined('DOING_AJAX')) { |
|
472 | - echo wp_json_encode(array('error' => $output)); |
|
473 | - exit(); |
|
474 | - } |
|
475 | - echo $output; |
|
476 | - die(); |
|
477 | - } |
|
478 | - |
|
479 | - |
|
480 | - |
|
481 | - /** |
|
482 | - * generate string from exception trace args |
|
483 | - * |
|
484 | - * @param array $arguments |
|
485 | - * @param bool $array |
|
486 | - * @return string |
|
487 | - */ |
|
488 | - private function _convert_args_to_string($arguments = array(), $array = false) |
|
489 | - { |
|
490 | - $arg_string = ''; |
|
491 | - if (! empty($arguments)) { |
|
492 | - $args = array(); |
|
493 | - foreach ($arguments as $arg) { |
|
494 | - if (! empty($arg)) { |
|
495 | - if (is_string($arg)) { |
|
496 | - $args[] = " '" . $arg . "'"; |
|
497 | - } elseif (is_array($arg)) { |
|
498 | - $args[] = 'ARRAY(' . $this->_convert_args_to_string($arg, true); |
|
499 | - } elseif ($arg === null) { |
|
500 | - $args[] = ' NULL'; |
|
501 | - } elseif (is_bool($arg)) { |
|
502 | - $args[] = ($arg) ? ' TRUE' : ' FALSE'; |
|
503 | - } elseif (is_object($arg)) { |
|
504 | - $args[] = ' OBJECT ' . get_class($arg); |
|
505 | - } elseif (is_resource($arg)) { |
|
506 | - $args[] = get_resource_type($arg); |
|
507 | - } else { |
|
508 | - $args[] = $arg; |
|
509 | - } |
|
510 | - } |
|
511 | - } |
|
512 | - $arg_string = implode(', ', $args); |
|
513 | - } |
|
514 | - if ($array) { |
|
515 | - $arg_string .= ' )'; |
|
516 | - } |
|
517 | - return $arg_string; |
|
518 | - } |
|
519 | - |
|
520 | - |
|
521 | - |
|
522 | - /** |
|
523 | - * add error message |
|
524 | - * |
|
525 | - * @param string $msg the message to display to users or developers - adding a double pipe || (OR) creates |
|
526 | - * separate messages for user || dev |
|
527 | - * @param string $file the file that the error occurred in - just use __FILE__ |
|
528 | - * @param string $func the function/method that the error occurred in - just use __FUNCTION__ |
|
529 | - * @param string $line the line number where the error occurred - just use __LINE__ |
|
530 | - * @return void |
|
531 | - */ |
|
532 | - public static function add_error($msg = null, $file = null, $func = null, $line = null) |
|
533 | - { |
|
534 | - self::_add_notice('errors', $msg, $file, $func, $line); |
|
535 | - self::$_error_count++; |
|
536 | - } |
|
537 | - |
|
538 | - |
|
539 | - |
|
540 | - /** |
|
541 | - * If WP_DEBUG is active, throws an exception. If WP_DEBUG is off, just |
|
542 | - * adds an error |
|
543 | - * |
|
544 | - * @param string $msg |
|
545 | - * @param string $file |
|
546 | - * @param string $func |
|
547 | - * @param string $line |
|
548 | - * @throws EE_Error |
|
549 | - */ |
|
550 | - public static function throw_exception_if_debugging($msg = null, $file = null, $func = null, $line = null) |
|
551 | - { |
|
552 | - if (WP_DEBUG) { |
|
553 | - throw new EE_Error($msg); |
|
554 | - } |
|
555 | - EE_Error::add_error($msg, $file, $func, $line); |
|
556 | - } |
|
557 | - |
|
558 | - |
|
559 | - |
|
560 | - /** |
|
561 | - * add success message |
|
562 | - * |
|
563 | - * @param string $msg the message to display to users or developers - adding a double pipe || (OR) creates |
|
564 | - * separate messages for user || dev |
|
565 | - * @param string $file the file that the error occurred in - just use __FILE__ |
|
566 | - * @param string $func the function/method that the error occurred in - just use __FUNCTION__ |
|
567 | - * @param string $line the line number where the error occurred - just use __LINE__ |
|
568 | - * @return void |
|
569 | - */ |
|
570 | - public static function add_success($msg = null, $file = null, $func = null, $line = null) |
|
571 | - { |
|
572 | - self::_add_notice('success', $msg, $file, $func, $line); |
|
573 | - } |
|
574 | - |
|
575 | - |
|
576 | - |
|
577 | - /** |
|
578 | - * add attention message |
|
579 | - * |
|
580 | - * @param string $msg the message to display to users or developers - adding a double pipe || (OR) creates |
|
581 | - * separate messages for user || dev |
|
582 | - * @param string $file the file that the error occurred in - just use __FILE__ |
|
583 | - * @param string $func the function/method that the error occurred in - just use __FUNCTION__ |
|
584 | - * @param string $line the line number where the error occurred - just use __LINE__ |
|
585 | - * @return void |
|
586 | - */ |
|
587 | - public static function add_attention($msg = null, $file = null, $func = null, $line = null) |
|
588 | - { |
|
589 | - self::_add_notice('attention', $msg, $file, $func, $line); |
|
590 | - } |
|
591 | - |
|
592 | - |
|
593 | - |
|
594 | - /** |
|
595 | - * add success message |
|
596 | - * |
|
597 | - * @param string $type whether the message is for a success or error notification |
|
598 | - * @param string $msg the message to display to users or developers - adding a double pipe || (OR) creates |
|
599 | - * separate messages for user || dev |
|
600 | - * @param string $file the file that the error occurred in - just use __FILE__ |
|
601 | - * @param string $func the function/method that the error occurred in - just use __FUNCTION__ |
|
602 | - * @param string $line the line number where the error occurred - just use __LINE__ |
|
603 | - * @return void |
|
604 | - */ |
|
605 | - private static function _add_notice($type = 'success', $msg = null, $file = null, $func = null, $line = null) |
|
606 | - { |
|
607 | - if (empty($msg)) { |
|
608 | - EE_Error::doing_it_wrong( |
|
609 | - 'EE_Error::add_' . $type . '()', |
|
610 | - sprintf( |
|
611 | - __('Notifications are not much use without a message! Please add a message to the EE_Error::add_%s() call made in %s on line %d', |
|
612 | - 'event_espresso'), |
|
613 | - $type, |
|
614 | - $file, |
|
615 | - $line |
|
616 | - ), |
|
617 | - EVENT_ESPRESSO_VERSION |
|
618 | - ); |
|
619 | - } |
|
620 | - if ($type === 'errors' && (empty($file) || empty($func) || empty($line))) { |
|
621 | - EE_Error::doing_it_wrong( |
|
622 | - 'EE_Error::add_error()', |
|
623 | - __('You need to provide the file name, function name, and line number that the error occurred on in order to better assist with debugging.', |
|
624 | - 'event_espresso'), |
|
625 | - EVENT_ESPRESSO_VERSION |
|
626 | - ); |
|
627 | - } |
|
628 | - // get separate user and developer messages if they exist |
|
629 | - $msg = explode('||', $msg); |
|
630 | - $user_msg = $msg[0]; |
|
631 | - $dev_msg = isset($msg[1]) ? $msg[1] : $msg[0]; |
|
632 | - /** |
|
633 | - * Do an action so other code can be triggered when a notice is created |
|
634 | - * |
|
635 | - * @param string $type can be 'errors', 'attention', or 'success' |
|
636 | - * @param string $user_msg message displayed to user when WP_DEBUG is off |
|
637 | - * @param string $user_msg message displayed to user when WP_DEBUG is on |
|
638 | - * @param string $file file where error was generated |
|
639 | - * @param string $func function where error was generated |
|
640 | - * @param string $line line where error was generated |
|
641 | - */ |
|
642 | - do_action('AHEE__EE_Error___add_notice', $type, $user_msg, $dev_msg, $file, $func, $line); |
|
643 | - $msg = WP_DEBUG ? $dev_msg : $user_msg; |
|
644 | - // add notice if message exists |
|
645 | - if (! empty($msg)) { |
|
646 | - // get error code |
|
647 | - $notice_code = EE_Error::generate_error_code($file, $func, $line); |
|
648 | - if (WP_DEBUG && $type === 'errors') { |
|
649 | - $msg .= '<br/><span class="tiny-text">' . $notice_code . '</span>'; |
|
650 | - } |
|
651 | - // add notice. Index by code if it's not blank |
|
652 | - if ($notice_code) { |
|
653 | - self::$_espresso_notices[$type][$notice_code] = $msg; |
|
654 | - } else { |
|
655 | - self::$_espresso_notices[$type][] = $msg; |
|
656 | - } |
|
657 | - add_action('wp_footer', array('EE_Error', 'enqueue_error_scripts'), 1); |
|
658 | - } |
|
659 | - } |
|
660 | - |
|
661 | - |
|
662 | - |
|
663 | - /** |
|
664 | - * in some case it may be necessary to overwrite the existing success messages |
|
665 | - * |
|
666 | - * @return void |
|
667 | - */ |
|
668 | - public static function overwrite_success() |
|
669 | - { |
|
670 | - self::$_espresso_notices['success'] = false; |
|
671 | - } |
|
672 | - |
|
673 | - |
|
674 | - |
|
675 | - /** |
|
676 | - * in some case it may be necessary to overwrite the existing attention messages |
|
677 | - * |
|
678 | - * @return void |
|
679 | - */ |
|
680 | - public static function overwrite_attention() |
|
681 | - { |
|
682 | - self::$_espresso_notices['attention'] = false; |
|
683 | - } |
|
684 | - |
|
685 | - |
|
686 | - |
|
687 | - /** |
|
688 | - * in some case it may be necessary to overwrite the existing error messages |
|
689 | - * |
|
690 | - * @return void |
|
691 | - */ |
|
692 | - public static function overwrite_errors() |
|
693 | - { |
|
694 | - self::$_espresso_notices['errors'] = false; |
|
695 | - } |
|
696 | - |
|
697 | - |
|
698 | - |
|
699 | - /** |
|
700 | - * reset_notices |
|
701 | - * |
|
702 | - * @return void |
|
703 | - */ |
|
704 | - public static function reset_notices() |
|
705 | - { |
|
706 | - self::$_espresso_notices['success'] = false; |
|
707 | - self::$_espresso_notices['attention'] = false; |
|
708 | - self::$_espresso_notices['errors'] = false; |
|
709 | - } |
|
710 | - |
|
711 | - |
|
712 | - |
|
713 | - /** |
|
714 | - * has_errors |
|
715 | - * |
|
716 | - * @return int |
|
717 | - */ |
|
718 | - public static function has_notices() |
|
719 | - { |
|
720 | - $has_notices = 0; |
|
721 | - // check for success messages |
|
722 | - $has_notices = self::$_espresso_notices['success'] && ! empty(self::$_espresso_notices['success']) |
|
723 | - ? 3 |
|
724 | - : $has_notices; |
|
725 | - // check for attention messages |
|
726 | - $has_notices = self::$_espresso_notices['attention'] && ! empty(self::$_espresso_notices['attention']) |
|
727 | - ? 2 |
|
728 | - : $has_notices; |
|
729 | - // check for error messages |
|
730 | - $has_notices = self::$_espresso_notices['errors'] && ! empty(self::$_espresso_notices['errors']) |
|
731 | - ? 1 |
|
732 | - : $has_notices; |
|
733 | - return $has_notices; |
|
734 | - } |
|
735 | - |
|
736 | - |
|
737 | - |
|
738 | - /** |
|
739 | - * This simply returns non formatted error notices as they were sent into the EE_Error object. |
|
740 | - * |
|
741 | - * @since 4.9.0 |
|
742 | - * @return array |
|
743 | - */ |
|
744 | - public static function get_vanilla_notices() |
|
745 | - { |
|
746 | - return array( |
|
747 | - 'success' => isset(self::$_espresso_notices['success']) |
|
748 | - ? self::$_espresso_notices['success'] |
|
749 | - : array(), |
|
750 | - 'attention' => isset(self::$_espresso_notices['attention']) |
|
751 | - ? self::$_espresso_notices['attention'] |
|
752 | - : array(), |
|
753 | - 'errors' => isset(self::$_espresso_notices['errors']) |
|
754 | - ? self::$_espresso_notices['errors'] |
|
755 | - : array(), |
|
756 | - ); |
|
757 | - } |
|
758 | - |
|
759 | - |
|
760 | - |
|
761 | - /** |
|
762 | - * compile all error or success messages into one string |
|
763 | - * |
|
764 | - * @see EE_Error::get_raw_notices if you want the raw notices without any preparations made to them |
|
765 | - * @param boolean $format_output whether or not to format the messages for display in the WP admin |
|
766 | - * @param boolean $save_to_transient whether or not to save notices to the db for retrieval on next request |
|
767 | - * - ONLY do this just before redirecting |
|
768 | - * @param boolean $remove_empty whether or not to unset empty messages |
|
769 | - * @return array |
|
770 | - */ |
|
771 | - public static function get_notices($format_output = true, $save_to_transient = false, $remove_empty = true) |
|
772 | - { |
|
773 | - do_action('AHEE_log', __FILE__, __FUNCTION__, ''); |
|
774 | - $success_messages = ''; |
|
775 | - $attention_messages = ''; |
|
776 | - $error_messages = ''; |
|
777 | - $print_scripts = false; |
|
778 | - // either save notices to the db |
|
779 | - if ($save_to_transient) { |
|
780 | - update_option('ee_notices', self::$_espresso_notices); |
|
781 | - return array(); |
|
782 | - } |
|
783 | - // grab any notices that have been previously saved |
|
784 | - if ($notices = get_option('ee_notices', false)) { |
|
785 | - foreach ($notices as $type => $notice) { |
|
786 | - if (is_array($notice) && ! empty($notice)) { |
|
787 | - // make sure that existing notice type is an array |
|
788 | - self::$_espresso_notices[$type] = is_array(self::$_espresso_notices[$type]) |
|
789 | - && ! empty(self::$_espresso_notices[$type]) |
|
790 | - ? self::$_espresso_notices[$type] : array(); |
|
791 | - // merge stored notices with any newly created ones |
|
792 | - self::$_espresso_notices[$type] = array_merge(self::$_espresso_notices[$type], $notice); |
|
793 | - $print_scripts = true; |
|
794 | - } |
|
795 | - } |
|
796 | - // now clear any stored notices |
|
797 | - update_option('ee_notices', false); |
|
798 | - } |
|
799 | - // check for success messages |
|
800 | - if (self::$_espresso_notices['success'] && ! empty(self::$_espresso_notices['success'])) { |
|
801 | - // combine messages |
|
802 | - $success_messages .= implode(self::$_espresso_notices['success'], '<br /><br />'); |
|
803 | - $print_scripts = true; |
|
804 | - } |
|
805 | - // check for attention messages |
|
806 | - if (self::$_espresso_notices['attention'] && ! empty(self::$_espresso_notices['attention'])) { |
|
807 | - // combine messages |
|
808 | - $attention_messages .= implode(self::$_espresso_notices['attention'], '<br /><br />'); |
|
809 | - $print_scripts = true; |
|
810 | - } |
|
811 | - // check for error messages |
|
812 | - if (self::$_espresso_notices['errors'] && ! empty(self::$_espresso_notices['errors'])) { |
|
813 | - $error_messages .= count(self::$_espresso_notices['errors']) > 1 |
|
814 | - ? __('The following errors have occurred:<br />', 'event_espresso') |
|
815 | - : __('An error has occurred:<br />', 'event_espresso'); |
|
816 | - // combine messages |
|
817 | - $error_messages .= implode(self::$_espresso_notices['errors'], '<br /><br />'); |
|
818 | - $print_scripts = true; |
|
819 | - } |
|
820 | - if ($format_output) { |
|
821 | - $notices = '<div id="espresso-notices">'; |
|
822 | - $close = is_admin() ? '' |
|
823 | - : '<a class="close-espresso-notice hide-if-no-js"><span class="dashicons dashicons-no"></span></a>'; |
|
824 | - if ($success_messages !== '') { |
|
825 | - $css_id = is_admin() ? 'message' : 'espresso-notices-success'; |
|
826 | - $css_class = is_admin() ? 'updated fade' : 'success fade-away'; |
|
827 | - //showMessage( $success_messages ); |
|
828 | - $notices .= '<div id="' |
|
829 | - . $css_id |
|
830 | - . '" class="espresso-notices ' |
|
831 | - . $css_class |
|
832 | - . '" style="display:none;"><p>' |
|
833 | - . $success_messages |
|
834 | - . '</p>' |
|
835 | - . $close |
|
836 | - . '</div>'; |
|
837 | - } |
|
838 | - if ($attention_messages !== '') { |
|
839 | - $css_id = is_admin() ? 'message' : 'espresso-notices-attention'; |
|
840 | - $css_class = is_admin() ? 'updated ee-notices-attention' : 'attention fade-away'; |
|
841 | - //showMessage( $error_messages, TRUE ); |
|
842 | - $notices .= '<div id="' |
|
843 | - . $css_id |
|
844 | - . '" class="espresso-notices ' |
|
845 | - . $css_class |
|
846 | - . '" style="display:none;"><p>' |
|
847 | - . $attention_messages |
|
848 | - . '</p>' |
|
849 | - . $close |
|
850 | - . '</div>'; |
|
851 | - } |
|
852 | - if ($error_messages !== '') { |
|
853 | - $css_id = is_admin() ? 'message' : 'espresso-notices-error'; |
|
854 | - $css_class = is_admin() ? 'error' : 'error fade-away'; |
|
855 | - //showMessage( $error_messages, TRUE ); |
|
856 | - $notices .= '<div id="' |
|
857 | - . $css_id |
|
858 | - . '" class="espresso-notices ' |
|
859 | - . $css_class |
|
860 | - . '" style="display:none;"><p>' |
|
861 | - . $error_messages |
|
862 | - . '</p>' |
|
863 | - . $close |
|
864 | - . '</div>'; |
|
865 | - } |
|
866 | - $notices .= '</div>'; |
|
867 | - } else { |
|
868 | - $notices = array( |
|
869 | - 'success' => $success_messages, |
|
870 | - 'attention' => $attention_messages, |
|
871 | - 'errors' => $error_messages, |
|
872 | - ); |
|
873 | - if ($remove_empty) { |
|
874 | - // remove empty notices |
|
875 | - foreach ($notices as $type => $notice) { |
|
876 | - if (empty($notice)) { |
|
877 | - unset($notices[$type]); |
|
878 | - } |
|
879 | - } |
|
880 | - } |
|
881 | - } |
|
882 | - if ($print_scripts) { |
|
883 | - self::_print_scripts(); |
|
884 | - } |
|
885 | - return $notices; |
|
886 | - } |
|
887 | - |
|
888 | - |
|
889 | - |
|
890 | - /** |
|
891 | - * add_persistent_admin_notice |
|
892 | - * |
|
893 | - * @param string $pan_name the name, or key of the Persistent Admin Notice to be stored |
|
894 | - * @param string $pan_message the message to be stored persistently until dismissed |
|
895 | - * @param bool $force_update allows one to enforce the reappearance of a persistent message. |
|
896 | - * @return void |
|
897 | - */ |
|
898 | - public static function add_persistent_admin_notice($pan_name = '', $pan_message, $force_update = false) |
|
899 | - { |
|
900 | - if (! empty($pan_name) && ! empty($pan_message)) { |
|
901 | - $persistent_admin_notices = get_option('ee_pers_admin_notices', array()); |
|
902 | - //maybe initialize persistent_admin_notices |
|
903 | - if (empty($persistent_admin_notices)) { |
|
904 | - add_option('ee_pers_admin_notices', array(), '', 'no'); |
|
905 | - } |
|
906 | - $pan_name = sanitize_key($pan_name); |
|
907 | - if (! array_key_exists($pan_name, $persistent_admin_notices) || $force_update) { |
|
908 | - $persistent_admin_notices[$pan_name] = $pan_message; |
|
909 | - update_option('ee_pers_admin_notices', $persistent_admin_notices); |
|
910 | - } |
|
911 | - } |
|
912 | - } |
|
913 | - |
|
914 | - |
|
915 | - |
|
916 | - /** |
|
917 | - * dismiss_persistent_admin_notice |
|
918 | - * |
|
919 | - * @param string $pan_name the name, or key of the Persistent Admin Notice to be dismissed |
|
920 | - * @param bool $purge |
|
921 | - * @param bool $return_immediately |
|
922 | - * @return void |
|
923 | - */ |
|
924 | - public static function dismiss_persistent_admin_notice($pan_name = '', $purge = false, $return_immediately = false) |
|
925 | - { |
|
926 | - $pan_name = EE_Registry::instance()->REQ->is_set('ee_nag_notice') |
|
927 | - ? EE_Registry::instance()->REQ->get('ee_nag_notice') |
|
928 | - : $pan_name; |
|
929 | - if (! empty($pan_name)) { |
|
930 | - $persistent_admin_notices = get_option('ee_pers_admin_notices', array()); |
|
931 | - // check if notice we wish to dismiss is actually in the $persistent_admin_notices array |
|
932 | - if (is_array($persistent_admin_notices) && isset($persistent_admin_notices[$pan_name])) { |
|
933 | - // completely delete nag notice, or just NULL message so that it can NOT be added again ? |
|
934 | - if ($purge) { |
|
935 | - unset($persistent_admin_notices[$pan_name]); |
|
936 | - } else { |
|
937 | - $persistent_admin_notices[$pan_name] = null; |
|
938 | - } |
|
939 | - if (update_option('ee_pers_admin_notices', $persistent_admin_notices) === false) { |
|
940 | - EE_Error::add_error(sprintf(__('The persistent admin notice for "%s" could not be deleted.', |
|
941 | - 'event_espresso'), $pan_name), __FILE__, __FUNCTION__, __LINE__); |
|
942 | - } |
|
943 | - } |
|
944 | - } |
|
945 | - if ($return_immediately) { |
|
946 | - return; |
|
947 | - } |
|
948 | - if (EE_Registry::instance()->REQ->ajax) { |
|
949 | - // grab any notices and concatenate into string |
|
950 | - echo wp_json_encode(array('errors' => implode('<br />', EE_Error::get_notices(false)))); |
|
951 | - exit(); |
|
952 | - } |
|
953 | - // save errors to a transient to be displayed on next request (after redirect) |
|
954 | - EE_Error::get_notices(false, true); |
|
955 | - $return_url = EE_Registry::instance()->REQ->is_set('return_url') |
|
956 | - ? EE_Registry::instance()->REQ->get('return_url') |
|
957 | - : ''; |
|
958 | - wp_safe_redirect(urldecode($return_url)); |
|
959 | - } |
|
960 | - |
|
961 | - |
|
962 | - |
|
963 | - /** |
|
964 | - * display_persistent_admin_notices |
|
965 | - * |
|
966 | - * @param string $pan_name the name, or key of the Persistent Admin Notice to be stored |
|
967 | - * @param string $pan_message the message to be stored persistently until dismissed |
|
968 | - * @param string $return_url URL to go back to after nag notice is dismissed |
|
969 | - * @return string |
|
970 | - */ |
|
971 | - public static function display_persistent_admin_notices($pan_name = '', $pan_message = '', $return_url = '') |
|
972 | - { |
|
973 | - if (! empty($pan_name) && ! empty($pan_message) && ! is_array( $pan_message )) { |
|
974 | - $args = array( |
|
975 | - 'nag_notice' => $pan_name, |
|
976 | - 'return_url' => urlencode($return_url), |
|
977 | - 'ajax_url' => WP_AJAX_URL, |
|
978 | - 'unknown_error' => esc_html__( |
|
979 | - 'An unknown error has occurred on the server while attempting to dismiss this notice.', |
|
980 | - 'event_espresso' |
|
981 | - ), |
|
982 | - ); |
|
983 | - EE_Registry::$i18n_js_strings = array_merge( |
|
984 | - EE_Registry::$i18n_js_strings, |
|
985 | - array('ee_dismiss' => $args) |
|
986 | - ); |
|
987 | - return ' |
|
470 | + $output .= self::_print_scripts(true); |
|
471 | + if (defined('DOING_AJAX')) { |
|
472 | + echo wp_json_encode(array('error' => $output)); |
|
473 | + exit(); |
|
474 | + } |
|
475 | + echo $output; |
|
476 | + die(); |
|
477 | + } |
|
478 | + |
|
479 | + |
|
480 | + |
|
481 | + /** |
|
482 | + * generate string from exception trace args |
|
483 | + * |
|
484 | + * @param array $arguments |
|
485 | + * @param bool $array |
|
486 | + * @return string |
|
487 | + */ |
|
488 | + private function _convert_args_to_string($arguments = array(), $array = false) |
|
489 | + { |
|
490 | + $arg_string = ''; |
|
491 | + if (! empty($arguments)) { |
|
492 | + $args = array(); |
|
493 | + foreach ($arguments as $arg) { |
|
494 | + if (! empty($arg)) { |
|
495 | + if (is_string($arg)) { |
|
496 | + $args[] = " '" . $arg . "'"; |
|
497 | + } elseif (is_array($arg)) { |
|
498 | + $args[] = 'ARRAY(' . $this->_convert_args_to_string($arg, true); |
|
499 | + } elseif ($arg === null) { |
|
500 | + $args[] = ' NULL'; |
|
501 | + } elseif (is_bool($arg)) { |
|
502 | + $args[] = ($arg) ? ' TRUE' : ' FALSE'; |
|
503 | + } elseif (is_object($arg)) { |
|
504 | + $args[] = ' OBJECT ' . get_class($arg); |
|
505 | + } elseif (is_resource($arg)) { |
|
506 | + $args[] = get_resource_type($arg); |
|
507 | + } else { |
|
508 | + $args[] = $arg; |
|
509 | + } |
|
510 | + } |
|
511 | + } |
|
512 | + $arg_string = implode(', ', $args); |
|
513 | + } |
|
514 | + if ($array) { |
|
515 | + $arg_string .= ' )'; |
|
516 | + } |
|
517 | + return $arg_string; |
|
518 | + } |
|
519 | + |
|
520 | + |
|
521 | + |
|
522 | + /** |
|
523 | + * add error message |
|
524 | + * |
|
525 | + * @param string $msg the message to display to users or developers - adding a double pipe || (OR) creates |
|
526 | + * separate messages for user || dev |
|
527 | + * @param string $file the file that the error occurred in - just use __FILE__ |
|
528 | + * @param string $func the function/method that the error occurred in - just use __FUNCTION__ |
|
529 | + * @param string $line the line number where the error occurred - just use __LINE__ |
|
530 | + * @return void |
|
531 | + */ |
|
532 | + public static function add_error($msg = null, $file = null, $func = null, $line = null) |
|
533 | + { |
|
534 | + self::_add_notice('errors', $msg, $file, $func, $line); |
|
535 | + self::$_error_count++; |
|
536 | + } |
|
537 | + |
|
538 | + |
|
539 | + |
|
540 | + /** |
|
541 | + * If WP_DEBUG is active, throws an exception. If WP_DEBUG is off, just |
|
542 | + * adds an error |
|
543 | + * |
|
544 | + * @param string $msg |
|
545 | + * @param string $file |
|
546 | + * @param string $func |
|
547 | + * @param string $line |
|
548 | + * @throws EE_Error |
|
549 | + */ |
|
550 | + public static function throw_exception_if_debugging($msg = null, $file = null, $func = null, $line = null) |
|
551 | + { |
|
552 | + if (WP_DEBUG) { |
|
553 | + throw new EE_Error($msg); |
|
554 | + } |
|
555 | + EE_Error::add_error($msg, $file, $func, $line); |
|
556 | + } |
|
557 | + |
|
558 | + |
|
559 | + |
|
560 | + /** |
|
561 | + * add success message |
|
562 | + * |
|
563 | + * @param string $msg the message to display to users or developers - adding a double pipe || (OR) creates |
|
564 | + * separate messages for user || dev |
|
565 | + * @param string $file the file that the error occurred in - just use __FILE__ |
|
566 | + * @param string $func the function/method that the error occurred in - just use __FUNCTION__ |
|
567 | + * @param string $line the line number where the error occurred - just use __LINE__ |
|
568 | + * @return void |
|
569 | + */ |
|
570 | + public static function add_success($msg = null, $file = null, $func = null, $line = null) |
|
571 | + { |
|
572 | + self::_add_notice('success', $msg, $file, $func, $line); |
|
573 | + } |
|
574 | + |
|
575 | + |
|
576 | + |
|
577 | + /** |
|
578 | + * add attention message |
|
579 | + * |
|
580 | + * @param string $msg the message to display to users or developers - adding a double pipe || (OR) creates |
|
581 | + * separate messages for user || dev |
|
582 | + * @param string $file the file that the error occurred in - just use __FILE__ |
|
583 | + * @param string $func the function/method that the error occurred in - just use __FUNCTION__ |
|
584 | + * @param string $line the line number where the error occurred - just use __LINE__ |
|
585 | + * @return void |
|
586 | + */ |
|
587 | + public static function add_attention($msg = null, $file = null, $func = null, $line = null) |
|
588 | + { |
|
589 | + self::_add_notice('attention', $msg, $file, $func, $line); |
|
590 | + } |
|
591 | + |
|
592 | + |
|
593 | + |
|
594 | + /** |
|
595 | + * add success message |
|
596 | + * |
|
597 | + * @param string $type whether the message is for a success or error notification |
|
598 | + * @param string $msg the message to display to users or developers - adding a double pipe || (OR) creates |
|
599 | + * separate messages for user || dev |
|
600 | + * @param string $file the file that the error occurred in - just use __FILE__ |
|
601 | + * @param string $func the function/method that the error occurred in - just use __FUNCTION__ |
|
602 | + * @param string $line the line number where the error occurred - just use __LINE__ |
|
603 | + * @return void |
|
604 | + */ |
|
605 | + private static function _add_notice($type = 'success', $msg = null, $file = null, $func = null, $line = null) |
|
606 | + { |
|
607 | + if (empty($msg)) { |
|
608 | + EE_Error::doing_it_wrong( |
|
609 | + 'EE_Error::add_' . $type . '()', |
|
610 | + sprintf( |
|
611 | + __('Notifications are not much use without a message! Please add a message to the EE_Error::add_%s() call made in %s on line %d', |
|
612 | + 'event_espresso'), |
|
613 | + $type, |
|
614 | + $file, |
|
615 | + $line |
|
616 | + ), |
|
617 | + EVENT_ESPRESSO_VERSION |
|
618 | + ); |
|
619 | + } |
|
620 | + if ($type === 'errors' && (empty($file) || empty($func) || empty($line))) { |
|
621 | + EE_Error::doing_it_wrong( |
|
622 | + 'EE_Error::add_error()', |
|
623 | + __('You need to provide the file name, function name, and line number that the error occurred on in order to better assist with debugging.', |
|
624 | + 'event_espresso'), |
|
625 | + EVENT_ESPRESSO_VERSION |
|
626 | + ); |
|
627 | + } |
|
628 | + // get separate user and developer messages if they exist |
|
629 | + $msg = explode('||', $msg); |
|
630 | + $user_msg = $msg[0]; |
|
631 | + $dev_msg = isset($msg[1]) ? $msg[1] : $msg[0]; |
|
632 | + /** |
|
633 | + * Do an action so other code can be triggered when a notice is created |
|
634 | + * |
|
635 | + * @param string $type can be 'errors', 'attention', or 'success' |
|
636 | + * @param string $user_msg message displayed to user when WP_DEBUG is off |
|
637 | + * @param string $user_msg message displayed to user when WP_DEBUG is on |
|
638 | + * @param string $file file where error was generated |
|
639 | + * @param string $func function where error was generated |
|
640 | + * @param string $line line where error was generated |
|
641 | + */ |
|
642 | + do_action('AHEE__EE_Error___add_notice', $type, $user_msg, $dev_msg, $file, $func, $line); |
|
643 | + $msg = WP_DEBUG ? $dev_msg : $user_msg; |
|
644 | + // add notice if message exists |
|
645 | + if (! empty($msg)) { |
|
646 | + // get error code |
|
647 | + $notice_code = EE_Error::generate_error_code($file, $func, $line); |
|
648 | + if (WP_DEBUG && $type === 'errors') { |
|
649 | + $msg .= '<br/><span class="tiny-text">' . $notice_code . '</span>'; |
|
650 | + } |
|
651 | + // add notice. Index by code if it's not blank |
|
652 | + if ($notice_code) { |
|
653 | + self::$_espresso_notices[$type][$notice_code] = $msg; |
|
654 | + } else { |
|
655 | + self::$_espresso_notices[$type][] = $msg; |
|
656 | + } |
|
657 | + add_action('wp_footer', array('EE_Error', 'enqueue_error_scripts'), 1); |
|
658 | + } |
|
659 | + } |
|
660 | + |
|
661 | + |
|
662 | + |
|
663 | + /** |
|
664 | + * in some case it may be necessary to overwrite the existing success messages |
|
665 | + * |
|
666 | + * @return void |
|
667 | + */ |
|
668 | + public static function overwrite_success() |
|
669 | + { |
|
670 | + self::$_espresso_notices['success'] = false; |
|
671 | + } |
|
672 | + |
|
673 | + |
|
674 | + |
|
675 | + /** |
|
676 | + * in some case it may be necessary to overwrite the existing attention messages |
|
677 | + * |
|
678 | + * @return void |
|
679 | + */ |
|
680 | + public static function overwrite_attention() |
|
681 | + { |
|
682 | + self::$_espresso_notices['attention'] = false; |
|
683 | + } |
|
684 | + |
|
685 | + |
|
686 | + |
|
687 | + /** |
|
688 | + * in some case it may be necessary to overwrite the existing error messages |
|
689 | + * |
|
690 | + * @return void |
|
691 | + */ |
|
692 | + public static function overwrite_errors() |
|
693 | + { |
|
694 | + self::$_espresso_notices['errors'] = false; |
|
695 | + } |
|
696 | + |
|
697 | + |
|
698 | + |
|
699 | + /** |
|
700 | + * reset_notices |
|
701 | + * |
|
702 | + * @return void |
|
703 | + */ |
|
704 | + public static function reset_notices() |
|
705 | + { |
|
706 | + self::$_espresso_notices['success'] = false; |
|
707 | + self::$_espresso_notices['attention'] = false; |
|
708 | + self::$_espresso_notices['errors'] = false; |
|
709 | + } |
|
710 | + |
|
711 | + |
|
712 | + |
|
713 | + /** |
|
714 | + * has_errors |
|
715 | + * |
|
716 | + * @return int |
|
717 | + */ |
|
718 | + public static function has_notices() |
|
719 | + { |
|
720 | + $has_notices = 0; |
|
721 | + // check for success messages |
|
722 | + $has_notices = self::$_espresso_notices['success'] && ! empty(self::$_espresso_notices['success']) |
|
723 | + ? 3 |
|
724 | + : $has_notices; |
|
725 | + // check for attention messages |
|
726 | + $has_notices = self::$_espresso_notices['attention'] && ! empty(self::$_espresso_notices['attention']) |
|
727 | + ? 2 |
|
728 | + : $has_notices; |
|
729 | + // check for error messages |
|
730 | + $has_notices = self::$_espresso_notices['errors'] && ! empty(self::$_espresso_notices['errors']) |
|
731 | + ? 1 |
|
732 | + : $has_notices; |
|
733 | + return $has_notices; |
|
734 | + } |
|
735 | + |
|
736 | + |
|
737 | + |
|
738 | + /** |
|
739 | + * This simply returns non formatted error notices as they were sent into the EE_Error object. |
|
740 | + * |
|
741 | + * @since 4.9.0 |
|
742 | + * @return array |
|
743 | + */ |
|
744 | + public static function get_vanilla_notices() |
|
745 | + { |
|
746 | + return array( |
|
747 | + 'success' => isset(self::$_espresso_notices['success']) |
|
748 | + ? self::$_espresso_notices['success'] |
|
749 | + : array(), |
|
750 | + 'attention' => isset(self::$_espresso_notices['attention']) |
|
751 | + ? self::$_espresso_notices['attention'] |
|
752 | + : array(), |
|
753 | + 'errors' => isset(self::$_espresso_notices['errors']) |
|
754 | + ? self::$_espresso_notices['errors'] |
|
755 | + : array(), |
|
756 | + ); |
|
757 | + } |
|
758 | + |
|
759 | + |
|
760 | + |
|
761 | + /** |
|
762 | + * compile all error or success messages into one string |
|
763 | + * |
|
764 | + * @see EE_Error::get_raw_notices if you want the raw notices without any preparations made to them |
|
765 | + * @param boolean $format_output whether or not to format the messages for display in the WP admin |
|
766 | + * @param boolean $save_to_transient whether or not to save notices to the db for retrieval on next request |
|
767 | + * - ONLY do this just before redirecting |
|
768 | + * @param boolean $remove_empty whether or not to unset empty messages |
|
769 | + * @return array |
|
770 | + */ |
|
771 | + public static function get_notices($format_output = true, $save_to_transient = false, $remove_empty = true) |
|
772 | + { |
|
773 | + do_action('AHEE_log', __FILE__, __FUNCTION__, ''); |
|
774 | + $success_messages = ''; |
|
775 | + $attention_messages = ''; |
|
776 | + $error_messages = ''; |
|
777 | + $print_scripts = false; |
|
778 | + // either save notices to the db |
|
779 | + if ($save_to_transient) { |
|
780 | + update_option('ee_notices', self::$_espresso_notices); |
|
781 | + return array(); |
|
782 | + } |
|
783 | + // grab any notices that have been previously saved |
|
784 | + if ($notices = get_option('ee_notices', false)) { |
|
785 | + foreach ($notices as $type => $notice) { |
|
786 | + if (is_array($notice) && ! empty($notice)) { |
|
787 | + // make sure that existing notice type is an array |
|
788 | + self::$_espresso_notices[$type] = is_array(self::$_espresso_notices[$type]) |
|
789 | + && ! empty(self::$_espresso_notices[$type]) |
|
790 | + ? self::$_espresso_notices[$type] : array(); |
|
791 | + // merge stored notices with any newly created ones |
|
792 | + self::$_espresso_notices[$type] = array_merge(self::$_espresso_notices[$type], $notice); |
|
793 | + $print_scripts = true; |
|
794 | + } |
|
795 | + } |
|
796 | + // now clear any stored notices |
|
797 | + update_option('ee_notices', false); |
|
798 | + } |
|
799 | + // check for success messages |
|
800 | + if (self::$_espresso_notices['success'] && ! empty(self::$_espresso_notices['success'])) { |
|
801 | + // combine messages |
|
802 | + $success_messages .= implode(self::$_espresso_notices['success'], '<br /><br />'); |
|
803 | + $print_scripts = true; |
|
804 | + } |
|
805 | + // check for attention messages |
|
806 | + if (self::$_espresso_notices['attention'] && ! empty(self::$_espresso_notices['attention'])) { |
|
807 | + // combine messages |
|
808 | + $attention_messages .= implode(self::$_espresso_notices['attention'], '<br /><br />'); |
|
809 | + $print_scripts = true; |
|
810 | + } |
|
811 | + // check for error messages |
|
812 | + if (self::$_espresso_notices['errors'] && ! empty(self::$_espresso_notices['errors'])) { |
|
813 | + $error_messages .= count(self::$_espresso_notices['errors']) > 1 |
|
814 | + ? __('The following errors have occurred:<br />', 'event_espresso') |
|
815 | + : __('An error has occurred:<br />', 'event_espresso'); |
|
816 | + // combine messages |
|
817 | + $error_messages .= implode(self::$_espresso_notices['errors'], '<br /><br />'); |
|
818 | + $print_scripts = true; |
|
819 | + } |
|
820 | + if ($format_output) { |
|
821 | + $notices = '<div id="espresso-notices">'; |
|
822 | + $close = is_admin() ? '' |
|
823 | + : '<a class="close-espresso-notice hide-if-no-js"><span class="dashicons dashicons-no"></span></a>'; |
|
824 | + if ($success_messages !== '') { |
|
825 | + $css_id = is_admin() ? 'message' : 'espresso-notices-success'; |
|
826 | + $css_class = is_admin() ? 'updated fade' : 'success fade-away'; |
|
827 | + //showMessage( $success_messages ); |
|
828 | + $notices .= '<div id="' |
|
829 | + . $css_id |
|
830 | + . '" class="espresso-notices ' |
|
831 | + . $css_class |
|
832 | + . '" style="display:none;"><p>' |
|
833 | + . $success_messages |
|
834 | + . '</p>' |
|
835 | + . $close |
|
836 | + . '</div>'; |
|
837 | + } |
|
838 | + if ($attention_messages !== '') { |
|
839 | + $css_id = is_admin() ? 'message' : 'espresso-notices-attention'; |
|
840 | + $css_class = is_admin() ? 'updated ee-notices-attention' : 'attention fade-away'; |
|
841 | + //showMessage( $error_messages, TRUE ); |
|
842 | + $notices .= '<div id="' |
|
843 | + . $css_id |
|
844 | + . '" class="espresso-notices ' |
|
845 | + . $css_class |
|
846 | + . '" style="display:none;"><p>' |
|
847 | + . $attention_messages |
|
848 | + . '</p>' |
|
849 | + . $close |
|
850 | + . '</div>'; |
|
851 | + } |
|
852 | + if ($error_messages !== '') { |
|
853 | + $css_id = is_admin() ? 'message' : 'espresso-notices-error'; |
|
854 | + $css_class = is_admin() ? 'error' : 'error fade-away'; |
|
855 | + //showMessage( $error_messages, TRUE ); |
|
856 | + $notices .= '<div id="' |
|
857 | + . $css_id |
|
858 | + . '" class="espresso-notices ' |
|
859 | + . $css_class |
|
860 | + . '" style="display:none;"><p>' |
|
861 | + . $error_messages |
|
862 | + . '</p>' |
|
863 | + . $close |
|
864 | + . '</div>'; |
|
865 | + } |
|
866 | + $notices .= '</div>'; |
|
867 | + } else { |
|
868 | + $notices = array( |
|
869 | + 'success' => $success_messages, |
|
870 | + 'attention' => $attention_messages, |
|
871 | + 'errors' => $error_messages, |
|
872 | + ); |
|
873 | + if ($remove_empty) { |
|
874 | + // remove empty notices |
|
875 | + foreach ($notices as $type => $notice) { |
|
876 | + if (empty($notice)) { |
|
877 | + unset($notices[$type]); |
|
878 | + } |
|
879 | + } |
|
880 | + } |
|
881 | + } |
|
882 | + if ($print_scripts) { |
|
883 | + self::_print_scripts(); |
|
884 | + } |
|
885 | + return $notices; |
|
886 | + } |
|
887 | + |
|
888 | + |
|
889 | + |
|
890 | + /** |
|
891 | + * add_persistent_admin_notice |
|
892 | + * |
|
893 | + * @param string $pan_name the name, or key of the Persistent Admin Notice to be stored |
|
894 | + * @param string $pan_message the message to be stored persistently until dismissed |
|
895 | + * @param bool $force_update allows one to enforce the reappearance of a persistent message. |
|
896 | + * @return void |
|
897 | + */ |
|
898 | + public static function add_persistent_admin_notice($pan_name = '', $pan_message, $force_update = false) |
|
899 | + { |
|
900 | + if (! empty($pan_name) && ! empty($pan_message)) { |
|
901 | + $persistent_admin_notices = get_option('ee_pers_admin_notices', array()); |
|
902 | + //maybe initialize persistent_admin_notices |
|
903 | + if (empty($persistent_admin_notices)) { |
|
904 | + add_option('ee_pers_admin_notices', array(), '', 'no'); |
|
905 | + } |
|
906 | + $pan_name = sanitize_key($pan_name); |
|
907 | + if (! array_key_exists($pan_name, $persistent_admin_notices) || $force_update) { |
|
908 | + $persistent_admin_notices[$pan_name] = $pan_message; |
|
909 | + update_option('ee_pers_admin_notices', $persistent_admin_notices); |
|
910 | + } |
|
911 | + } |
|
912 | + } |
|
913 | + |
|
914 | + |
|
915 | + |
|
916 | + /** |
|
917 | + * dismiss_persistent_admin_notice |
|
918 | + * |
|
919 | + * @param string $pan_name the name, or key of the Persistent Admin Notice to be dismissed |
|
920 | + * @param bool $purge |
|
921 | + * @param bool $return_immediately |
|
922 | + * @return void |
|
923 | + */ |
|
924 | + public static function dismiss_persistent_admin_notice($pan_name = '', $purge = false, $return_immediately = false) |
|
925 | + { |
|
926 | + $pan_name = EE_Registry::instance()->REQ->is_set('ee_nag_notice') |
|
927 | + ? EE_Registry::instance()->REQ->get('ee_nag_notice') |
|
928 | + : $pan_name; |
|
929 | + if (! empty($pan_name)) { |
|
930 | + $persistent_admin_notices = get_option('ee_pers_admin_notices', array()); |
|
931 | + // check if notice we wish to dismiss is actually in the $persistent_admin_notices array |
|
932 | + if (is_array($persistent_admin_notices) && isset($persistent_admin_notices[$pan_name])) { |
|
933 | + // completely delete nag notice, or just NULL message so that it can NOT be added again ? |
|
934 | + if ($purge) { |
|
935 | + unset($persistent_admin_notices[$pan_name]); |
|
936 | + } else { |
|
937 | + $persistent_admin_notices[$pan_name] = null; |
|
938 | + } |
|
939 | + if (update_option('ee_pers_admin_notices', $persistent_admin_notices) === false) { |
|
940 | + EE_Error::add_error(sprintf(__('The persistent admin notice for "%s" could not be deleted.', |
|
941 | + 'event_espresso'), $pan_name), __FILE__, __FUNCTION__, __LINE__); |
|
942 | + } |
|
943 | + } |
|
944 | + } |
|
945 | + if ($return_immediately) { |
|
946 | + return; |
|
947 | + } |
|
948 | + if (EE_Registry::instance()->REQ->ajax) { |
|
949 | + // grab any notices and concatenate into string |
|
950 | + echo wp_json_encode(array('errors' => implode('<br />', EE_Error::get_notices(false)))); |
|
951 | + exit(); |
|
952 | + } |
|
953 | + // save errors to a transient to be displayed on next request (after redirect) |
|
954 | + EE_Error::get_notices(false, true); |
|
955 | + $return_url = EE_Registry::instance()->REQ->is_set('return_url') |
|
956 | + ? EE_Registry::instance()->REQ->get('return_url') |
|
957 | + : ''; |
|
958 | + wp_safe_redirect(urldecode($return_url)); |
|
959 | + } |
|
960 | + |
|
961 | + |
|
962 | + |
|
963 | + /** |
|
964 | + * display_persistent_admin_notices |
|
965 | + * |
|
966 | + * @param string $pan_name the name, or key of the Persistent Admin Notice to be stored |
|
967 | + * @param string $pan_message the message to be stored persistently until dismissed |
|
968 | + * @param string $return_url URL to go back to after nag notice is dismissed |
|
969 | + * @return string |
|
970 | + */ |
|
971 | + public static function display_persistent_admin_notices($pan_name = '', $pan_message = '', $return_url = '') |
|
972 | + { |
|
973 | + if (! empty($pan_name) && ! empty($pan_message) && ! is_array( $pan_message )) { |
|
974 | + $args = array( |
|
975 | + 'nag_notice' => $pan_name, |
|
976 | + 'return_url' => urlencode($return_url), |
|
977 | + 'ajax_url' => WP_AJAX_URL, |
|
978 | + 'unknown_error' => esc_html__( |
|
979 | + 'An unknown error has occurred on the server while attempting to dismiss this notice.', |
|
980 | + 'event_espresso' |
|
981 | + ), |
|
982 | + ); |
|
983 | + EE_Registry::$i18n_js_strings = array_merge( |
|
984 | + EE_Registry::$i18n_js_strings, |
|
985 | + array('ee_dismiss' => $args) |
|
986 | + ); |
|
987 | + return ' |
|
988 | 988 | <div id="' |
989 | - . $pan_name |
|
990 | - . '" class="espresso-notices updated ee-nag-notice clearfix" style="border-left: 4px solid #fcb93c;"> |
|
989 | + . $pan_name |
|
990 | + . '" class="espresso-notices updated ee-nag-notice clearfix" style="border-left: 4px solid #fcb93c;"> |
|
991 | 991 | <p>' |
992 | - . $pan_message |
|
993 | - . '</p> |
|
992 | + . $pan_message |
|
993 | + . '</p> |
|
994 | 994 | <a class="dismiss-ee-nag-notice hide-if-no-js" style="float: right; cursor: pointer; text-decoration:none;" rel="' |
995 | - . $pan_name |
|
996 | - . '"> |
|
995 | + . $pan_name |
|
996 | + . '"> |
|
997 | 997 | <span class="dashicons dashicons-dismiss" style="position:relative; top:-1px; margin-right:.25em;"></span>' |
998 | - . __('Dismiss', 'event_espresso') |
|
999 | - . ' |
|
998 | + . __('Dismiss', 'event_espresso') |
|
999 | + . ' |
|
1000 | 1000 | </a> |
1001 | 1001 | <div style="clear:both;"></div> |
1002 | 1002 | </div>'; |
1003 | - } |
|
1004 | - return ''; |
|
1005 | - } |
|
1006 | - |
|
1007 | - |
|
1008 | - |
|
1009 | - /** |
|
1010 | - * get_persistent_admin_notices |
|
1011 | - * |
|
1012 | - * @param string $return_url |
|
1013 | - * @return string |
|
1014 | - */ |
|
1015 | - public static function get_persistent_admin_notices($return_url = '') |
|
1016 | - { |
|
1017 | - $notices = ''; |
|
1018 | - // check for persistent admin notices |
|
1019 | - //filter the list though so plugins can notify the admin in a different way if they want |
|
1020 | - $persistent_admin_notices = apply_filters( |
|
1021 | - 'FHEE__EE_Error__get_persistent_admin_notices', |
|
1022 | - get_option('ee_pers_admin_notices', false), |
|
1023 | - 'ee_pers_admin_notices', |
|
1024 | - $return_url |
|
1025 | - ); |
|
1026 | - if ($persistent_admin_notices) { |
|
1027 | - // load scripts |
|
1028 | - wp_register_script( |
|
1029 | - 'espresso_core', |
|
1030 | - EE_GLOBAL_ASSETS_URL . 'scripts/espresso_core.js', |
|
1031 | - array('jquery'), |
|
1032 | - EVENT_ESPRESSO_VERSION, |
|
1033 | - true |
|
1034 | - ); |
|
1035 | - wp_register_script( |
|
1036 | - 'ee_error_js', |
|
1037 | - EE_GLOBAL_ASSETS_URL . 'scripts/EE_Error.js', |
|
1038 | - array('espresso_core'), |
|
1039 | - EVENT_ESPRESSO_VERSION, |
|
1040 | - true |
|
1041 | - ); |
|
1042 | - wp_enqueue_script('ee_error_js'); |
|
1043 | - // and display notices |
|
1044 | - foreach ($persistent_admin_notices as $pan_name => $pan_message) { |
|
1045 | - $notices .= self::display_persistent_admin_notices($pan_name, $pan_message, $return_url); |
|
1046 | - } |
|
1047 | - } |
|
1048 | - return $notices; |
|
1049 | - } |
|
1050 | - |
|
1051 | - |
|
1052 | - |
|
1053 | - /** |
|
1054 | - * _print_scripts |
|
1055 | - * |
|
1056 | - * @param bool $force_print |
|
1057 | - * @return string |
|
1058 | - */ |
|
1059 | - private static function _print_scripts($force_print = false) |
|
1060 | - { |
|
1061 | - if (! $force_print && (did_action('admin_enqueue_scripts') || did_action('wp_enqueue_scripts'))) { |
|
1062 | - if (wp_script_is('ee_error_js', 'enqueued')) { |
|
1063 | - return ''; |
|
1064 | - } |
|
1065 | - if (wp_script_is('ee_error_js', 'registered')) { |
|
1066 | - wp_enqueue_style('espresso_default'); |
|
1067 | - wp_enqueue_style('espresso_custom_css'); |
|
1068 | - wp_enqueue_script('ee_error_js'); |
|
1069 | - wp_localize_script('ee_error_js', 'ee_settings', array('wp_debug' => WP_DEBUG)); |
|
1070 | - } |
|
1071 | - } else { |
|
1072 | - return ' |
|
1003 | + } |
|
1004 | + return ''; |
|
1005 | + } |
|
1006 | + |
|
1007 | + |
|
1008 | + |
|
1009 | + /** |
|
1010 | + * get_persistent_admin_notices |
|
1011 | + * |
|
1012 | + * @param string $return_url |
|
1013 | + * @return string |
|
1014 | + */ |
|
1015 | + public static function get_persistent_admin_notices($return_url = '') |
|
1016 | + { |
|
1017 | + $notices = ''; |
|
1018 | + // check for persistent admin notices |
|
1019 | + //filter the list though so plugins can notify the admin in a different way if they want |
|
1020 | + $persistent_admin_notices = apply_filters( |
|
1021 | + 'FHEE__EE_Error__get_persistent_admin_notices', |
|
1022 | + get_option('ee_pers_admin_notices', false), |
|
1023 | + 'ee_pers_admin_notices', |
|
1024 | + $return_url |
|
1025 | + ); |
|
1026 | + if ($persistent_admin_notices) { |
|
1027 | + // load scripts |
|
1028 | + wp_register_script( |
|
1029 | + 'espresso_core', |
|
1030 | + EE_GLOBAL_ASSETS_URL . 'scripts/espresso_core.js', |
|
1031 | + array('jquery'), |
|
1032 | + EVENT_ESPRESSO_VERSION, |
|
1033 | + true |
|
1034 | + ); |
|
1035 | + wp_register_script( |
|
1036 | + 'ee_error_js', |
|
1037 | + EE_GLOBAL_ASSETS_URL . 'scripts/EE_Error.js', |
|
1038 | + array('espresso_core'), |
|
1039 | + EVENT_ESPRESSO_VERSION, |
|
1040 | + true |
|
1041 | + ); |
|
1042 | + wp_enqueue_script('ee_error_js'); |
|
1043 | + // and display notices |
|
1044 | + foreach ($persistent_admin_notices as $pan_name => $pan_message) { |
|
1045 | + $notices .= self::display_persistent_admin_notices($pan_name, $pan_message, $return_url); |
|
1046 | + } |
|
1047 | + } |
|
1048 | + return $notices; |
|
1049 | + } |
|
1050 | + |
|
1051 | + |
|
1052 | + |
|
1053 | + /** |
|
1054 | + * _print_scripts |
|
1055 | + * |
|
1056 | + * @param bool $force_print |
|
1057 | + * @return string |
|
1058 | + */ |
|
1059 | + private static function _print_scripts($force_print = false) |
|
1060 | + { |
|
1061 | + if (! $force_print && (did_action('admin_enqueue_scripts') || did_action('wp_enqueue_scripts'))) { |
|
1062 | + if (wp_script_is('ee_error_js', 'enqueued')) { |
|
1063 | + return ''; |
|
1064 | + } |
|
1065 | + if (wp_script_is('ee_error_js', 'registered')) { |
|
1066 | + wp_enqueue_style('espresso_default'); |
|
1067 | + wp_enqueue_style('espresso_custom_css'); |
|
1068 | + wp_enqueue_script('ee_error_js'); |
|
1069 | + wp_localize_script('ee_error_js', 'ee_settings', array('wp_debug' => WP_DEBUG)); |
|
1070 | + } |
|
1071 | + } else { |
|
1072 | + return ' |
|
1073 | 1073 | <script> |
1074 | 1074 | /* <![CDATA[ */ |
1075 | 1075 | var ee_settings = {"wp_debug":"' . WP_DEBUG . '"}; |
@@ -1079,143 +1079,143 @@ discard block |
||
1079 | 1079 | <script src="' . EE_GLOBAL_ASSETS_URL . 'scripts/espresso_core.js' . '?ver=' . espresso_version() . '" type="text/javascript"></script> |
1080 | 1080 | <script src="' . EE_GLOBAL_ASSETS_URL . 'scripts/EE_Error.js' . '?ver=' . espresso_version() . '" type="text/javascript"></script> |
1081 | 1081 | '; |
1082 | - } |
|
1083 | - return ''; |
|
1084 | - } |
|
1085 | - |
|
1086 | - |
|
1087 | - |
|
1088 | - /** |
|
1089 | - * enqueue_error_scripts |
|
1090 | - * |
|
1091 | - * @return void |
|
1092 | - */ |
|
1093 | - public static function enqueue_error_scripts() |
|
1094 | - { |
|
1095 | - self::_print_scripts(); |
|
1096 | - } |
|
1097 | - |
|
1098 | - |
|
1099 | - |
|
1100 | - /** |
|
1101 | - * create error code from filepath, function name, |
|
1102 | - * and line number where exception or error was thrown |
|
1103 | - * |
|
1104 | - * @param string $file |
|
1105 | - * @param string $func |
|
1106 | - * @param string $line |
|
1107 | - * @return string |
|
1108 | - */ |
|
1109 | - public static function generate_error_code($file = '', $func = '', $line = '') |
|
1110 | - { |
|
1111 | - $file = explode('.', basename($file)); |
|
1112 | - $error_code = ! empty($file[0]) ? $file[0] : ''; |
|
1113 | - $error_code .= ! empty($func) ? ' - ' . $func : ''; |
|
1114 | - $error_code .= ! empty($line) ? ' - ' . $line : ''; |
|
1115 | - return $error_code; |
|
1116 | - } |
|
1117 | - |
|
1118 | - |
|
1119 | - |
|
1120 | - /** |
|
1121 | - * write exception details to log file |
|
1122 | - * |
|
1123 | - * @param int $time |
|
1124 | - * @param array $ex |
|
1125 | - * @param bool $clear |
|
1126 | - * @return void |
|
1127 | - */ |
|
1128 | - public function write_to_error_log($time = 0, $ex = array(), $clear = false) |
|
1129 | - { |
|
1130 | - if (empty($ex)) { |
|
1131 | - return; |
|
1132 | - } |
|
1133 | - if (! $time) { |
|
1134 | - $time = time(); |
|
1135 | - } |
|
1136 | - $exception_log = '----------------------------------------------------------------------------------------' |
|
1137 | - . PHP_EOL; |
|
1138 | - $exception_log .= '[' . date('Y-m-d H:i:s', $time) . '] Exception Details' . PHP_EOL; |
|
1139 | - $exception_log .= 'Message: ' . $ex['msg'] . PHP_EOL; |
|
1140 | - $exception_log .= 'Code: ' . $ex['code'] . PHP_EOL; |
|
1141 | - $exception_log .= 'File: ' . $ex['file'] . PHP_EOL; |
|
1142 | - $exception_log .= 'Line No: ' . $ex['line'] . PHP_EOL; |
|
1143 | - $exception_log .= 'Stack trace: ' . PHP_EOL; |
|
1144 | - $exception_log .= $ex['string'] . PHP_EOL; |
|
1145 | - $exception_log .= '----------------------------------------------------------------------------------------' |
|
1146 | - . PHP_EOL; |
|
1147 | - try { |
|
1148 | - EEH_File::ensure_file_exists_and_is_writable( |
|
1149 | - EVENT_ESPRESSO_UPLOAD_DIR . 'logs' . DS . self::$_exception_log_file |
|
1150 | - ); |
|
1151 | - EEH_File::add_htaccess_deny_from_all(EVENT_ESPRESSO_UPLOAD_DIR . 'logs'); |
|
1152 | - if (! $clear) { |
|
1153 | - //get existing log file and append new log info |
|
1154 | - $exception_log = EEH_File::get_file_contents( |
|
1155 | - EVENT_ESPRESSO_UPLOAD_DIR . 'logs' . DS . self::$_exception_log_file |
|
1156 | - ) . $exception_log; |
|
1157 | - } |
|
1158 | - EEH_File::write_to_file( |
|
1159 | - EVENT_ESPRESSO_UPLOAD_DIR . 'logs' . DS . self::$_exception_log_file, |
|
1160 | - $exception_log |
|
1161 | - ); |
|
1162 | - } catch (EE_Error $e) { |
|
1163 | - EE_Error::add_error(sprintf(__('Event Espresso error logging could not be setup because: %s', |
|
1164 | - 'event_espresso'), $e->getMessage())); |
|
1165 | - return; |
|
1166 | - } |
|
1167 | - } |
|
1168 | - |
|
1169 | - |
|
1170 | - |
|
1171 | - /** |
|
1172 | - * This is just a wrapper for the EEH_Debug_Tools::instance()->doing_it_wrong() method. |
|
1173 | - * doing_it_wrong() is used in those cases where a normal PHP error won't get thrown, |
|
1174 | - * but the code execution is done in a manner that could lead to unexpected results |
|
1175 | - * (i.e. running to early, or too late in WP or EE loading process). |
|
1176 | - * A good test for knowing whether to use this method is: |
|
1177 | - * 1. Is there going to be a PHP error if something isn't setup/used correctly? |
|
1178 | - * Yes -> use EE_Error::add_error() or throw new EE_Error() |
|
1179 | - * 2. If this is loaded before something else, it won't break anything, |
|
1180 | - * but just wont' do what its supposed to do? Yes -> use EE_Error::doing_it_wrong() |
|
1181 | - * |
|
1182 | - * @uses constant WP_DEBUG test if wp_debug is on or not |
|
1183 | - * @param string $function The function that was called |
|
1184 | - * @param string $message A message explaining what has been done incorrectly |
|
1185 | - * @param string $version The version of Event Espresso where the error was added |
|
1186 | - * @param string $applies_when a version string for when you want the doing_it_wrong notice to begin appearing |
|
1187 | - * for a deprecated function. This allows deprecation to occur during one version, |
|
1188 | - * but not have any notices appear until a later version. This allows developers |
|
1189 | - * extra time to update their code before notices appear. |
|
1190 | - * @param int $error_type |
|
1191 | - */ |
|
1192 | - public static function doing_it_wrong( |
|
1193 | - $function, |
|
1194 | - $message, |
|
1195 | - $version, |
|
1196 | - $applies_when = '', |
|
1197 | - $error_type = null |
|
1198 | - ) { |
|
1199 | - if (defined('WP_DEBUG') && WP_DEBUG) { |
|
1200 | - EEH_Debug_Tools::instance()->doing_it_wrong($function, $message, $version, $applies_when, $error_type); |
|
1201 | - } |
|
1202 | - } |
|
1203 | - |
|
1204 | - |
|
1205 | - |
|
1206 | - /** |
|
1207 | - * Like get_notices, but returns an array of all the notices of the given type. |
|
1208 | - * |
|
1209 | - * @return array { |
|
1210 | - * @type array $success all the success messages |
|
1211 | - * @type array $errors all the error messages |
|
1212 | - * @type array $attention all the attention messages |
|
1213 | - * } |
|
1214 | - */ |
|
1215 | - public static function get_raw_notices() |
|
1216 | - { |
|
1217 | - return self::$_espresso_notices; |
|
1218 | - } |
|
1082 | + } |
|
1083 | + return ''; |
|
1084 | + } |
|
1085 | + |
|
1086 | + |
|
1087 | + |
|
1088 | + /** |
|
1089 | + * enqueue_error_scripts |
|
1090 | + * |
|
1091 | + * @return void |
|
1092 | + */ |
|
1093 | + public static function enqueue_error_scripts() |
|
1094 | + { |
|
1095 | + self::_print_scripts(); |
|
1096 | + } |
|
1097 | + |
|
1098 | + |
|
1099 | + |
|
1100 | + /** |
|
1101 | + * create error code from filepath, function name, |
|
1102 | + * and line number where exception or error was thrown |
|
1103 | + * |
|
1104 | + * @param string $file |
|
1105 | + * @param string $func |
|
1106 | + * @param string $line |
|
1107 | + * @return string |
|
1108 | + */ |
|
1109 | + public static function generate_error_code($file = '', $func = '', $line = '') |
|
1110 | + { |
|
1111 | + $file = explode('.', basename($file)); |
|
1112 | + $error_code = ! empty($file[0]) ? $file[0] : ''; |
|
1113 | + $error_code .= ! empty($func) ? ' - ' . $func : ''; |
|
1114 | + $error_code .= ! empty($line) ? ' - ' . $line : ''; |
|
1115 | + return $error_code; |
|
1116 | + } |
|
1117 | + |
|
1118 | + |
|
1119 | + |
|
1120 | + /** |
|
1121 | + * write exception details to log file |
|
1122 | + * |
|
1123 | + * @param int $time |
|
1124 | + * @param array $ex |
|
1125 | + * @param bool $clear |
|
1126 | + * @return void |
|
1127 | + */ |
|
1128 | + public function write_to_error_log($time = 0, $ex = array(), $clear = false) |
|
1129 | + { |
|
1130 | + if (empty($ex)) { |
|
1131 | + return; |
|
1132 | + } |
|
1133 | + if (! $time) { |
|
1134 | + $time = time(); |
|
1135 | + } |
|
1136 | + $exception_log = '----------------------------------------------------------------------------------------' |
|
1137 | + . PHP_EOL; |
|
1138 | + $exception_log .= '[' . date('Y-m-d H:i:s', $time) . '] Exception Details' . PHP_EOL; |
|
1139 | + $exception_log .= 'Message: ' . $ex['msg'] . PHP_EOL; |
|
1140 | + $exception_log .= 'Code: ' . $ex['code'] . PHP_EOL; |
|
1141 | + $exception_log .= 'File: ' . $ex['file'] . PHP_EOL; |
|
1142 | + $exception_log .= 'Line No: ' . $ex['line'] . PHP_EOL; |
|
1143 | + $exception_log .= 'Stack trace: ' . PHP_EOL; |
|
1144 | + $exception_log .= $ex['string'] . PHP_EOL; |
|
1145 | + $exception_log .= '----------------------------------------------------------------------------------------' |
|
1146 | + . PHP_EOL; |
|
1147 | + try { |
|
1148 | + EEH_File::ensure_file_exists_and_is_writable( |
|
1149 | + EVENT_ESPRESSO_UPLOAD_DIR . 'logs' . DS . self::$_exception_log_file |
|
1150 | + ); |
|
1151 | + EEH_File::add_htaccess_deny_from_all(EVENT_ESPRESSO_UPLOAD_DIR . 'logs'); |
|
1152 | + if (! $clear) { |
|
1153 | + //get existing log file and append new log info |
|
1154 | + $exception_log = EEH_File::get_file_contents( |
|
1155 | + EVENT_ESPRESSO_UPLOAD_DIR . 'logs' . DS . self::$_exception_log_file |
|
1156 | + ) . $exception_log; |
|
1157 | + } |
|
1158 | + EEH_File::write_to_file( |
|
1159 | + EVENT_ESPRESSO_UPLOAD_DIR . 'logs' . DS . self::$_exception_log_file, |
|
1160 | + $exception_log |
|
1161 | + ); |
|
1162 | + } catch (EE_Error $e) { |
|
1163 | + EE_Error::add_error(sprintf(__('Event Espresso error logging could not be setup because: %s', |
|
1164 | + 'event_espresso'), $e->getMessage())); |
|
1165 | + return; |
|
1166 | + } |
|
1167 | + } |
|
1168 | + |
|
1169 | + |
|
1170 | + |
|
1171 | + /** |
|
1172 | + * This is just a wrapper for the EEH_Debug_Tools::instance()->doing_it_wrong() method. |
|
1173 | + * doing_it_wrong() is used in those cases where a normal PHP error won't get thrown, |
|
1174 | + * but the code execution is done in a manner that could lead to unexpected results |
|
1175 | + * (i.e. running to early, or too late in WP or EE loading process). |
|
1176 | + * A good test for knowing whether to use this method is: |
|
1177 | + * 1. Is there going to be a PHP error if something isn't setup/used correctly? |
|
1178 | + * Yes -> use EE_Error::add_error() or throw new EE_Error() |
|
1179 | + * 2. If this is loaded before something else, it won't break anything, |
|
1180 | + * but just wont' do what its supposed to do? Yes -> use EE_Error::doing_it_wrong() |
|
1181 | + * |
|
1182 | + * @uses constant WP_DEBUG test if wp_debug is on or not |
|
1183 | + * @param string $function The function that was called |
|
1184 | + * @param string $message A message explaining what has been done incorrectly |
|
1185 | + * @param string $version The version of Event Espresso where the error was added |
|
1186 | + * @param string $applies_when a version string for when you want the doing_it_wrong notice to begin appearing |
|
1187 | + * for a deprecated function. This allows deprecation to occur during one version, |
|
1188 | + * but not have any notices appear until a later version. This allows developers |
|
1189 | + * extra time to update their code before notices appear. |
|
1190 | + * @param int $error_type |
|
1191 | + */ |
|
1192 | + public static function doing_it_wrong( |
|
1193 | + $function, |
|
1194 | + $message, |
|
1195 | + $version, |
|
1196 | + $applies_when = '', |
|
1197 | + $error_type = null |
|
1198 | + ) { |
|
1199 | + if (defined('WP_DEBUG') && WP_DEBUG) { |
|
1200 | + EEH_Debug_Tools::instance()->doing_it_wrong($function, $message, $version, $applies_when, $error_type); |
|
1201 | + } |
|
1202 | + } |
|
1203 | + |
|
1204 | + |
|
1205 | + |
|
1206 | + /** |
|
1207 | + * Like get_notices, but returns an array of all the notices of the given type. |
|
1208 | + * |
|
1209 | + * @return array { |
|
1210 | + * @type array $success all the success messages |
|
1211 | + * @type array $errors all the error messages |
|
1212 | + * @type array $attention all the attention messages |
|
1213 | + * } |
|
1214 | + */ |
|
1215 | + public static function get_raw_notices() |
|
1216 | + { |
|
1217 | + return self::$_espresso_notices; |
|
1218 | + } |
|
1219 | 1219 | |
1220 | 1220 | |
1221 | 1221 | |
@@ -1231,27 +1231,27 @@ discard block |
||
1231 | 1231 | */ |
1232 | 1232 | function espresso_error_enqueue_scripts() |
1233 | 1233 | { |
1234 | - // js for error handling |
|
1235 | - wp_register_script( |
|
1236 | - 'espresso_core', |
|
1237 | - EE_GLOBAL_ASSETS_URL . 'scripts/espresso_core.js', |
|
1238 | - array('jquery'), |
|
1239 | - EVENT_ESPRESSO_VERSION, |
|
1240 | - false |
|
1241 | - ); |
|
1242 | - wp_register_script( |
|
1243 | - 'ee_error_js', |
|
1244 | - EE_GLOBAL_ASSETS_URL . 'scripts/EE_Error.js', |
|
1245 | - array('espresso_core'), |
|
1246 | - EVENT_ESPRESSO_VERSION, |
|
1247 | - false |
|
1248 | - ); |
|
1234 | + // js for error handling |
|
1235 | + wp_register_script( |
|
1236 | + 'espresso_core', |
|
1237 | + EE_GLOBAL_ASSETS_URL . 'scripts/espresso_core.js', |
|
1238 | + array('jquery'), |
|
1239 | + EVENT_ESPRESSO_VERSION, |
|
1240 | + false |
|
1241 | + ); |
|
1242 | + wp_register_script( |
|
1243 | + 'ee_error_js', |
|
1244 | + EE_GLOBAL_ASSETS_URL . 'scripts/EE_Error.js', |
|
1245 | + array('espresso_core'), |
|
1246 | + EVENT_ESPRESSO_VERSION, |
|
1247 | + false |
|
1248 | + ); |
|
1249 | 1249 | } |
1250 | 1250 | |
1251 | 1251 | if (is_admin()) { |
1252 | - add_action('admin_enqueue_scripts', 'espresso_error_enqueue_scripts', 2); |
|
1252 | + add_action('admin_enqueue_scripts', 'espresso_error_enqueue_scripts', 2); |
|
1253 | 1253 | } else { |
1254 | - add_action('wp_enqueue_scripts', 'espresso_error_enqueue_scripts', 2); |
|
1254 | + add_action('wp_enqueue_scripts', 'espresso_error_enqueue_scripts', 2); |
|
1255 | 1255 | } |
1256 | 1256 | |
1257 | 1257 |
@@ -19,1488 +19,1488 @@ |
||
19 | 19 | class EE_Registry implements ResettableInterface |
20 | 20 | { |
21 | 21 | |
22 | - /** |
|
23 | - * EE_Registry Object |
|
24 | - * |
|
25 | - * @var EE_Registry $_instance |
|
26 | - * @access private |
|
27 | - */ |
|
28 | - private static $_instance = null; |
|
29 | - |
|
30 | - /** |
|
31 | - * @var EE_Dependency_Map $_dependency_map |
|
32 | - * @access protected |
|
33 | - */ |
|
34 | - protected $_dependency_map = null; |
|
35 | - |
|
36 | - /** |
|
37 | - * @var array $_class_abbreviations |
|
38 | - * @access protected |
|
39 | - */ |
|
40 | - protected $_class_abbreviations = array(); |
|
41 | - |
|
42 | - /** |
|
43 | - * @access public |
|
44 | - * @var \EventEspresso\core\services\commands\CommandBusInterface $BUS |
|
45 | - */ |
|
46 | - public $BUS; |
|
47 | - |
|
48 | - /** |
|
49 | - * EE_Cart Object |
|
50 | - * |
|
51 | - * @access public |
|
52 | - * @var EE_Cart $CART |
|
53 | - */ |
|
54 | - public $CART = null; |
|
55 | - |
|
56 | - /** |
|
57 | - * EE_Config Object |
|
58 | - * |
|
59 | - * @access public |
|
60 | - * @var EE_Config $CFG |
|
61 | - */ |
|
62 | - public $CFG = null; |
|
63 | - |
|
64 | - /** |
|
65 | - * EE_Network_Config Object |
|
66 | - * |
|
67 | - * @access public |
|
68 | - * @var EE_Network_Config $NET_CFG |
|
69 | - */ |
|
70 | - public $NET_CFG = null; |
|
71 | - |
|
72 | - /** |
|
73 | - * StdClass object for storing library classes in |
|
74 | - * |
|
75 | - * @public LIB |
|
76 | - * @var StdClass $LIB |
|
77 | - */ |
|
78 | - public $LIB = null; |
|
79 | - |
|
80 | - /** |
|
81 | - * EE_Request_Handler Object |
|
82 | - * |
|
83 | - * @access public |
|
84 | - * @var EE_Request_Handler $REQ |
|
85 | - */ |
|
86 | - public $REQ = null; |
|
87 | - |
|
88 | - /** |
|
89 | - * EE_Session Object |
|
90 | - * |
|
91 | - * @access public |
|
92 | - * @var EE_Session $SSN |
|
93 | - */ |
|
94 | - public $SSN = null; |
|
95 | - |
|
96 | - /** |
|
97 | - * holds the ee capabilities object. |
|
98 | - * |
|
99 | - * @since 4.5.0 |
|
100 | - * @var EE_Capabilities |
|
101 | - */ |
|
102 | - public $CAP = null; |
|
103 | - |
|
104 | - /** |
|
105 | - * holds the EE_Message_Resource_Manager object. |
|
106 | - * |
|
107 | - * @since 4.9.0 |
|
108 | - * @var EE_Message_Resource_Manager |
|
109 | - */ |
|
110 | - public $MRM = null; |
|
111 | - |
|
112 | - |
|
113 | - /** |
|
114 | - * Holds the Assets Registry instance |
|
115 | - * @var Registry |
|
116 | - */ |
|
117 | - public $AssetsRegistry = null; |
|
118 | - |
|
119 | - /** |
|
120 | - * $addons - StdClass object for holding addons which have registered themselves to work with EE core |
|
121 | - * |
|
122 | - * @access public |
|
123 | - * @var EE_Addon[] |
|
124 | - */ |
|
125 | - public $addons = null; |
|
126 | - |
|
127 | - /** |
|
128 | - * $models |
|
129 | - * @access public |
|
130 | - * @var EEM_Base[] $models keys are 'short names' (eg Event), values are class names (eg 'EEM_Event') |
|
131 | - */ |
|
132 | - public $models = array(); |
|
133 | - |
|
134 | - /** |
|
135 | - * $modules |
|
136 | - * @access public |
|
137 | - * @var EED_Module[] $modules |
|
138 | - */ |
|
139 | - public $modules = null; |
|
140 | - |
|
141 | - /** |
|
142 | - * $shortcodes |
|
143 | - * @access public |
|
144 | - * @var EES_Shortcode[] $shortcodes |
|
145 | - */ |
|
146 | - public $shortcodes = null; |
|
147 | - |
|
148 | - /** |
|
149 | - * $widgets |
|
150 | - * @access public |
|
151 | - * @var WP_Widget[] $widgets |
|
152 | - */ |
|
153 | - public $widgets = null; |
|
154 | - |
|
155 | - /** |
|
156 | - * $non_abstract_db_models |
|
157 | - * @access public |
|
158 | - * @var array this is an array of all implemented model names (i.e. not the parent abstract models, or models |
|
159 | - * which don't actually fetch items from the DB in the normal way (ie, are not children of EEM_Base)). |
|
160 | - * Keys are model "short names" (eg "Event") as used in model relations, and values are |
|
161 | - * classnames (eg "EEM_Event") |
|
162 | - */ |
|
163 | - public $non_abstract_db_models = array(); |
|
164 | - |
|
165 | - |
|
166 | - /** |
|
167 | - * $i18n_js_strings - internationalization for JS strings |
|
168 | - * usage: EE_Registry::i18n_js_strings['string_key'] = __( 'string to translate.', 'event_espresso' ); |
|
169 | - * in js file: var translatedString = eei18n.string_key; |
|
170 | - * |
|
171 | - * @access public |
|
172 | - * @var array |
|
173 | - */ |
|
174 | - public static $i18n_js_strings = array(); |
|
175 | - |
|
176 | - |
|
177 | - /** |
|
178 | - * $main_file - path to espresso.php |
|
179 | - * |
|
180 | - * @access public |
|
181 | - * @var array |
|
182 | - */ |
|
183 | - public $main_file; |
|
184 | - |
|
185 | - /** |
|
186 | - * array of ReflectionClass objects where the key is the class name |
|
187 | - * |
|
188 | - * @access public |
|
189 | - * @var ReflectionClass[] |
|
190 | - */ |
|
191 | - public $_reflectors; |
|
192 | - |
|
193 | - /** |
|
194 | - * boolean flag to indicate whether or not to load/save dependencies from/to the cache |
|
195 | - * |
|
196 | - * @access protected |
|
197 | - * @var boolean $_cache_on |
|
198 | - */ |
|
199 | - protected $_cache_on = true; |
|
200 | - |
|
201 | - |
|
202 | - |
|
203 | - /** |
|
204 | - * @singleton method used to instantiate class object |
|
205 | - * @access public |
|
206 | - * @param \EE_Dependency_Map $dependency_map |
|
207 | - * @return \EE_Registry instance |
|
208 | - */ |
|
209 | - public static function instance(\EE_Dependency_Map $dependency_map = null) |
|
210 | - { |
|
211 | - // check if class object is instantiated |
|
212 | - if ( ! self::$_instance instanceof EE_Registry) { |
|
213 | - self::$_instance = new EE_Registry($dependency_map); |
|
214 | - } |
|
215 | - return self::$_instance; |
|
216 | - } |
|
217 | - |
|
218 | - |
|
219 | - |
|
220 | - /** |
|
221 | - *protected constructor to prevent direct creation |
|
222 | - * |
|
223 | - * @Constructor |
|
224 | - * @access protected |
|
225 | - * @param \EE_Dependency_Map $dependency_map |
|
226 | - */ |
|
227 | - protected function __construct(\EE_Dependency_Map $dependency_map) |
|
228 | - { |
|
229 | - $this->_dependency_map = $dependency_map; |
|
230 | - $this->LIB = new stdClass(); |
|
231 | - $this->addons = new stdClass(); |
|
232 | - $this->modules = new stdClass(); |
|
233 | - $this->shortcodes = new stdClass(); |
|
234 | - $this->widgets = new stdClass(); |
|
235 | - add_action('EE_Load_Espresso_Core__handle_request__initialize_core_loading', array($this, 'initialize')); |
|
236 | - } |
|
237 | - |
|
238 | - |
|
239 | - |
|
240 | - /** |
|
241 | - * initialize |
|
242 | - */ |
|
243 | - public function initialize() |
|
244 | - { |
|
245 | - $this->_class_abbreviations = apply_filters( |
|
246 | - 'FHEE__EE_Registry____construct___class_abbreviations', |
|
247 | - array( |
|
248 | - 'EE_Config' => 'CFG', |
|
249 | - 'EE_Session' => 'SSN', |
|
250 | - 'EE_Capabilities' => 'CAP', |
|
251 | - 'EE_Cart' => 'CART', |
|
252 | - 'EE_Network_Config' => 'NET_CFG', |
|
253 | - 'EE_Request_Handler' => 'REQ', |
|
254 | - 'EE_Message_Resource_Manager' => 'MRM', |
|
255 | - 'EventEspresso\core\services\commands\CommandBus' => 'BUS', |
|
256 | - 'EventEspresso\core\services\assets\Registry' => 'AssetsRegistry', |
|
257 | - ) |
|
258 | - ); |
|
259 | - $this->load_core('Base', array(), true); |
|
260 | - // add our request and response objects to the cache |
|
261 | - $request_loader = $this->_dependency_map->class_loader('EE_Request'); |
|
262 | - $this->_set_cached_class( |
|
263 | - $request_loader(), |
|
264 | - 'EE_Request' |
|
265 | - ); |
|
266 | - $response_loader = $this->_dependency_map->class_loader('EE_Response'); |
|
267 | - $this->_set_cached_class( |
|
268 | - $response_loader(), |
|
269 | - 'EE_Response' |
|
270 | - ); |
|
271 | - add_action('AHEE__EE_System__set_hooks_for_core', array($this, 'init')); |
|
272 | - } |
|
273 | - |
|
274 | - |
|
275 | - |
|
276 | - /** |
|
277 | - * init |
|
278 | - * |
|
279 | - * @access public |
|
280 | - * @return void |
|
281 | - */ |
|
282 | - public function init() |
|
283 | - { |
|
284 | - // Get current page protocol |
|
285 | - $protocol = isset($_SERVER['HTTPS']) ? 'https://' : 'http://'; |
|
286 | - // Output admin-ajax.php URL with same protocol as current page |
|
287 | - self::$i18n_js_strings['ajax_url'] = admin_url('admin-ajax.php', $protocol); |
|
288 | - self::$i18n_js_strings['wp_debug'] = defined('WP_DEBUG') ? WP_DEBUG : false; |
|
289 | - } |
|
290 | - |
|
291 | - |
|
292 | - |
|
293 | - /** |
|
294 | - * localize_i18n_js_strings |
|
295 | - * |
|
296 | - * @return string |
|
297 | - */ |
|
298 | - public static function localize_i18n_js_strings() |
|
299 | - { |
|
300 | - $i18n_js_strings = (array)EE_Registry::$i18n_js_strings; |
|
301 | - foreach ($i18n_js_strings as $key => $value) { |
|
302 | - if (is_scalar($value)) { |
|
303 | - $i18n_js_strings[$key] = html_entity_decode((string)$value, ENT_QUOTES, 'UTF-8'); |
|
304 | - } |
|
305 | - } |
|
306 | - return "/* <![CDATA[ */ var eei18n = " . wp_json_encode($i18n_js_strings) . '; /* ]]> */'; |
|
307 | - } |
|
308 | - |
|
309 | - |
|
310 | - |
|
311 | - /** |
|
312 | - * @param mixed string | EED_Module $module |
|
313 | - */ |
|
314 | - public function add_module($module) |
|
315 | - { |
|
316 | - if ($module instanceof EED_Module) { |
|
317 | - $module_class = get_class($module); |
|
318 | - $this->modules->{$module_class} = $module; |
|
319 | - } else { |
|
320 | - if ( ! class_exists('EE_Module_Request_Router', false)) { |
|
321 | - $this->load_core('Module_Request_Router'); |
|
322 | - } |
|
323 | - $this->modules->{$module} = EE_Module_Request_Router::module_factory($module); |
|
324 | - } |
|
325 | - } |
|
326 | - |
|
327 | - |
|
328 | - |
|
329 | - /** |
|
330 | - * @param string $module_name |
|
331 | - * @return mixed EED_Module | NULL |
|
332 | - */ |
|
333 | - public function get_module($module_name = '') |
|
334 | - { |
|
335 | - return isset($this->modules->{$module_name}) ? $this->modules->{$module_name} : null; |
|
336 | - } |
|
337 | - |
|
338 | - |
|
339 | - |
|
340 | - /** |
|
341 | - * loads core classes - must be singletons |
|
342 | - * |
|
343 | - * @access public |
|
344 | - * @param string $class_name - simple class name ie: session |
|
345 | - * @param mixed $arguments |
|
346 | - * @param bool $load_only |
|
347 | - * @return mixed |
|
348 | - */ |
|
349 | - public function load_core($class_name, $arguments = array(), $load_only = false) |
|
350 | - { |
|
351 | - $core_paths = apply_filters( |
|
352 | - 'FHEE__EE_Registry__load_core__core_paths', |
|
353 | - array( |
|
354 | - EE_CORE, |
|
355 | - EE_ADMIN, |
|
356 | - EE_CPTS, |
|
357 | - EE_CORE . 'data_migration_scripts' . DS, |
|
358 | - EE_CORE . 'request_stack' . DS, |
|
359 | - EE_CORE . 'middleware' . DS, |
|
360 | - ) |
|
361 | - ); |
|
362 | - // retrieve instantiated class |
|
363 | - return $this->_load($core_paths, 'EE_', $class_name, 'core', $arguments, false, true, $load_only); |
|
364 | - } |
|
365 | - |
|
366 | - |
|
367 | - |
|
368 | - /** |
|
369 | - * loads service classes |
|
370 | - * |
|
371 | - * @access public |
|
372 | - * @param string $class_name - simple class name ie: session |
|
373 | - * @param mixed $arguments |
|
374 | - * @param bool $load_only |
|
375 | - * @return mixed |
|
376 | - */ |
|
377 | - public function load_service($class_name, $arguments = array(), $load_only = false) |
|
378 | - { |
|
379 | - $service_paths = apply_filters( |
|
380 | - 'FHEE__EE_Registry__load_service__service_paths', |
|
381 | - array( |
|
382 | - EE_CORE . 'services' . DS, |
|
383 | - ) |
|
384 | - ); |
|
385 | - // retrieve instantiated class |
|
386 | - return $this->_load($service_paths, 'EE_', $class_name, 'class', $arguments, false, true, $load_only); |
|
387 | - } |
|
388 | - |
|
389 | - |
|
390 | - |
|
391 | - /** |
|
392 | - * loads data_migration_scripts |
|
393 | - * |
|
394 | - * @access public |
|
395 | - * @param string $class_name - class name for the DMS ie: EE_DMS_Core_4_2_0 |
|
396 | - * @param mixed $arguments |
|
397 | - * @return EE_Data_Migration_Script_Base|mixed |
|
398 | - */ |
|
399 | - public function load_dms($class_name, $arguments = array()) |
|
400 | - { |
|
401 | - // retrieve instantiated class |
|
402 | - return $this->_load(EE_Data_Migration_Manager::instance()->get_data_migration_script_folders(), 'EE_DMS_', $class_name, 'dms', $arguments, false, false, false); |
|
403 | - } |
|
404 | - |
|
405 | - |
|
406 | - |
|
407 | - /** |
|
408 | - * loads object creating classes - must be singletons |
|
409 | - * |
|
410 | - * @param string $class_name - simple class name ie: attendee |
|
411 | - * @param mixed $arguments - an array of arguments to pass to the class |
|
412 | - * @param bool $from_db - some classes are instantiated from the db and thus call a different method to instantiate |
|
413 | - * @param bool $cache if you don't want the class to be stored in the internal cache (non-persistent) then set this to FALSE (ie. when instantiating model objects from client in a loop) |
|
414 | - * @param bool $load_only whether or not to just load the file and NOT instantiate, or load AND instantiate (default) |
|
415 | - * @return EE_Base_Class | bool |
|
416 | - */ |
|
417 | - public function load_class($class_name, $arguments = array(), $from_db = false, $cache = true, $load_only = false) |
|
418 | - { |
|
419 | - $paths = apply_filters('FHEE__EE_Registry__load_class__paths', array( |
|
420 | - EE_CORE, |
|
421 | - EE_CLASSES, |
|
422 | - EE_BUSINESS, |
|
423 | - )); |
|
424 | - // retrieve instantiated class |
|
425 | - return $this->_load($paths, 'EE_', $class_name, 'class', $arguments, $from_db, $cache, $load_only); |
|
426 | - } |
|
427 | - |
|
428 | - |
|
429 | - |
|
430 | - /** |
|
431 | - * loads helper classes - must be singletons |
|
432 | - * |
|
433 | - * @param string $class_name - simple class name ie: price |
|
434 | - * @param mixed $arguments |
|
435 | - * @param bool $load_only |
|
436 | - * @return EEH_Base | bool |
|
437 | - */ |
|
438 | - public function load_helper($class_name, $arguments = array(), $load_only = true) |
|
439 | - { |
|
440 | - // todo: add doing_it_wrong() in a few versions after all addons have had calls to this method removed |
|
441 | - $helper_paths = apply_filters('FHEE__EE_Registry__load_helper__helper_paths', array(EE_HELPERS)); |
|
442 | - // retrieve instantiated class |
|
443 | - return $this->_load($helper_paths, 'EEH_', $class_name, 'helper', $arguments, false, true, $load_only); |
|
444 | - } |
|
445 | - |
|
446 | - |
|
447 | - |
|
448 | - /** |
|
449 | - * loads core classes - must be singletons |
|
450 | - * |
|
451 | - * @access public |
|
452 | - * @param string $class_name - simple class name ie: session |
|
453 | - * @param mixed $arguments |
|
454 | - * @param bool $load_only |
|
455 | - * @param bool $cache whether to cache the object or not. |
|
456 | - * @return mixed |
|
457 | - */ |
|
458 | - public function load_lib($class_name, $arguments = array(), $load_only = false, $cache = true) |
|
459 | - { |
|
460 | - $paths = array( |
|
461 | - EE_LIBRARIES, |
|
462 | - EE_LIBRARIES . 'messages' . DS, |
|
463 | - EE_LIBRARIES . 'shortcodes' . DS, |
|
464 | - EE_LIBRARIES . 'qtips' . DS, |
|
465 | - EE_LIBRARIES . 'payment_methods' . DS, |
|
466 | - EE_LIBRARIES . 'messages' . DS . 'defaults' . DS, |
|
467 | - ); |
|
468 | - // retrieve instantiated class |
|
469 | - return $this->_load($paths, 'EE_', $class_name, 'lib', $arguments, false, $cache, $load_only); |
|
470 | - } |
|
471 | - |
|
472 | - |
|
473 | - |
|
474 | - /** |
|
475 | - * loads model classes - must be singletons |
|
476 | - * |
|
477 | - * @param string $class_name - simple class name ie: price |
|
478 | - * @param mixed $arguments |
|
479 | - * @param bool $load_only |
|
480 | - * @return EEM_Base | bool |
|
481 | - */ |
|
482 | - public function load_model($class_name, $arguments = array(), $load_only = false) |
|
483 | - { |
|
484 | - $paths = apply_filters('FHEE__EE_Registry__load_model__paths', array( |
|
485 | - EE_MODELS, |
|
486 | - EE_CORE, |
|
487 | - )); |
|
488 | - // retrieve instantiated class |
|
489 | - return $this->_load($paths, 'EEM_', $class_name, 'model', $arguments, false, true, $load_only); |
|
490 | - } |
|
491 | - |
|
492 | - |
|
493 | - |
|
494 | - /** |
|
495 | - * loads model classes - must be singletons |
|
496 | - * |
|
497 | - * @param string $class_name - simple class name ie: price |
|
498 | - * @param mixed $arguments |
|
499 | - * @param bool $load_only |
|
500 | - * @return mixed | bool |
|
501 | - */ |
|
502 | - public function load_model_class($class_name, $arguments = array(), $load_only = true) |
|
503 | - { |
|
504 | - $paths = array( |
|
505 | - EE_MODELS . 'fields' . DS, |
|
506 | - EE_MODELS . 'helpers' . DS, |
|
507 | - EE_MODELS . 'relations' . DS, |
|
508 | - EE_MODELS . 'strategies' . DS, |
|
509 | - ); |
|
510 | - // retrieve instantiated class |
|
511 | - return $this->_load($paths, 'EE_', $class_name, '', $arguments, false, true, $load_only); |
|
512 | - } |
|
513 | - |
|
514 | - |
|
515 | - |
|
516 | - /** |
|
517 | - * Determines if $model_name is the name of an actual EE model. |
|
518 | - * |
|
519 | - * @param string $model_name like Event, Attendee, Question_Group_Question, etc. |
|
520 | - * @return boolean |
|
521 | - */ |
|
522 | - public function is_model_name($model_name) |
|
523 | - { |
|
524 | - return isset($this->models[$model_name]) ? true : false; |
|
525 | - } |
|
526 | - |
|
527 | - |
|
528 | - |
|
529 | - /** |
|
530 | - * generic class loader |
|
531 | - * |
|
532 | - * @param string $path_to_file - directory path to file location, not including filename |
|
533 | - * @param string $file_name - file name ie: my_file.php, including extension |
|
534 | - * @param string $type - file type - core? class? helper? model? |
|
535 | - * @param mixed $arguments |
|
536 | - * @param bool $load_only |
|
537 | - * @return mixed |
|
538 | - */ |
|
539 | - public function load_file($path_to_file, $file_name, $type = '', $arguments = array(), $load_only = true) |
|
540 | - { |
|
541 | - // retrieve instantiated class |
|
542 | - return $this->_load($path_to_file, '', $file_name, $type, $arguments, false, true, $load_only); |
|
543 | - } |
|
544 | - |
|
545 | - |
|
546 | - |
|
547 | - /** |
|
548 | - * load_addon |
|
549 | - * |
|
550 | - * @param string $path_to_file - directory path to file location, not including filename |
|
551 | - * @param string $class_name - full class name ie: My_Class |
|
552 | - * @param string $type - file type - core? class? helper? model? |
|
553 | - * @param mixed $arguments |
|
554 | - * @param bool $load_only |
|
555 | - * @return EE_Addon |
|
556 | - */ |
|
557 | - public function load_addon($path_to_file, $class_name, $type = 'class', $arguments = array(), $load_only = false) |
|
558 | - { |
|
559 | - // retrieve instantiated class |
|
560 | - return $this->_load($path_to_file, 'addon', $class_name, $type, $arguments, false, true, $load_only); |
|
561 | - } |
|
562 | - |
|
563 | - |
|
564 | - |
|
565 | - /** |
|
566 | - * instantiates, caches, and automatically resolves dependencies |
|
567 | - * for classes that use a Fully Qualified Class Name. |
|
568 | - * if the class is not capable of being loaded using PSR-4 autoloading, |
|
569 | - * then you need to use one of the existing load_*() methods |
|
570 | - * which can resolve the classname and filepath from the passed arguments |
|
571 | - * |
|
572 | - * @param bool|string $class_name Fully Qualified Class Name |
|
573 | - * @param array $arguments an argument, or array of arguments to pass to the class upon instantiation |
|
574 | - * @param bool $cache whether to cache the instantiated object for reuse |
|
575 | - * @param bool $from_db some classes are instantiated from the db |
|
576 | - * and thus call a different method to instantiate |
|
577 | - * @param bool $load_only if true, will only load the file, but will NOT instantiate an object |
|
578 | - * @param bool|string $addon if true, will cache the object in the EE_Registry->$addons array |
|
579 | - * @return mixed null = failure to load or instantiate class object. |
|
580 | - * object = class loaded and instantiated successfully. |
|
581 | - * bool = fail or success when $load_only is true |
|
582 | - */ |
|
583 | - public function create( |
|
584 | - $class_name = false, |
|
585 | - $arguments = array(), |
|
586 | - $cache = false, |
|
587 | - $from_db = false, |
|
588 | - $load_only = false, |
|
589 | - $addon = false |
|
590 | - ) { |
|
591 | - $class_name = ltrim($class_name, '\\'); |
|
592 | - $class_name = $this->_dependency_map->get_alias($class_name); |
|
593 | - if ( ! class_exists($class_name)) { |
|
594 | - // maybe the class is registered with a preceding \ |
|
595 | - $class_name = strpos($class_name, '\\') !== 0 ? '\\' . $class_name : $class_name; |
|
596 | - // still doesn't exist ? |
|
597 | - if ( ! class_exists($class_name)) { |
|
598 | - return null; |
|
599 | - } |
|
600 | - } |
|
601 | - // if we're only loading the class and it already exists, then let's just return true immediately |
|
602 | - if ($load_only) { |
|
603 | - return true; |
|
604 | - } |
|
605 | - $addon = $addon ? 'addon' : ''; |
|
606 | - // $this->_cache_on is toggled during the recursive loading that can occur with dependency injection |
|
607 | - // $cache is controlled by individual calls to separate Registry loader methods like load_class() |
|
608 | - // $load_only is also controlled by individual calls to separate Registry loader methods like load_file() |
|
609 | - if ($this->_cache_on && $cache && ! $load_only) { |
|
610 | - // return object if it's already cached |
|
611 | - $cached_class = $this->_get_cached_class($class_name, $addon); |
|
612 | - if ($cached_class !== null) { |
|
613 | - return $cached_class; |
|
614 | - } |
|
615 | - } |
|
616 | - // instantiate the requested object |
|
617 | - $class_obj = $this->_create_object($class_name, $arguments, $addon, $from_db); |
|
618 | - if ($this->_cache_on && $cache) { |
|
619 | - // save it for later... kinda like gum { : $ |
|
620 | - $this->_set_cached_class($class_obj, $class_name, $addon, $from_db); |
|
621 | - } |
|
622 | - $this->_cache_on = true; |
|
623 | - return $class_obj; |
|
624 | - } |
|
625 | - |
|
626 | - |
|
627 | - |
|
628 | - /** |
|
629 | - * instantiates, caches, and injects dependencies for classes |
|
630 | - * |
|
631 | - * @param array $file_paths an array of paths to folders to look in |
|
632 | - * @param string $class_prefix EE or EEM or... ??? |
|
633 | - * @param bool|string $class_name $class name |
|
634 | - * @param string $type file type - core? class? helper? model? |
|
635 | - * @param mixed $arguments an argument or array of arguments to pass to the class upon instantiation |
|
636 | - * @param bool $from_db some classes are instantiated from the db |
|
637 | - * and thus call a different method to instantiate |
|
638 | - * @param bool $cache whether to cache the instantiated object for reuse |
|
639 | - * @param bool $load_only if true, will only load the file, but will NOT instantiate an object |
|
640 | - * @return null|object|bool null = failure to load or instantiate class object. |
|
641 | - * object = class loaded and instantiated successfully. |
|
642 | - * bool = fail or success when $load_only is true |
|
643 | - */ |
|
644 | - protected function _load( |
|
645 | - $file_paths = array(), |
|
646 | - $class_prefix = 'EE_', |
|
647 | - $class_name = false, |
|
648 | - $type = 'class', |
|
649 | - $arguments = array(), |
|
650 | - $from_db = false, |
|
651 | - $cache = true, |
|
652 | - $load_only = false |
|
653 | - ) { |
|
654 | - $class_name = ltrim($class_name, '\\'); |
|
655 | - // strip php file extension |
|
656 | - $class_name = str_replace('.php', '', trim($class_name)); |
|
657 | - // does the class have a prefix ? |
|
658 | - if ( ! empty($class_prefix) && $class_prefix != 'addon') { |
|
659 | - // make sure $class_prefix is uppercase |
|
660 | - $class_prefix = strtoupper(trim($class_prefix)); |
|
661 | - // add class prefix ONCE!!! |
|
662 | - $class_name = $class_prefix . str_replace($class_prefix, '', $class_name); |
|
663 | - } |
|
664 | - $class_name = $this->_dependency_map->get_alias($class_name); |
|
665 | - $class_exists = class_exists($class_name, false); |
|
666 | - // if we're only loading the class and it already exists, then let's just return true immediately |
|
667 | - if ($load_only && $class_exists) { |
|
668 | - return true; |
|
669 | - } |
|
670 | - // $this->_cache_on is toggled during the recursive loading that can occur with dependency injection |
|
671 | - // $cache is controlled by individual calls to separate Registry loader methods like load_class() |
|
672 | - // $load_only is also controlled by individual calls to separate Registry loader methods like load_file() |
|
673 | - if ($this->_cache_on && $cache && ! $load_only) { |
|
674 | - // return object if it's already cached |
|
675 | - $cached_class = $this->_get_cached_class($class_name, $class_prefix); |
|
676 | - if ($cached_class !== null) { |
|
677 | - return $cached_class; |
|
678 | - } |
|
679 | - } |
|
680 | - // if the class doesn't already exist.. then we need to try and find the file and load it |
|
681 | - if ( ! $class_exists) { |
|
682 | - // get full path to file |
|
683 | - $path = $this->_resolve_path($class_name, $type, $file_paths); |
|
684 | - // load the file |
|
685 | - $loaded = $this->_require_file($path, $class_name, $type, $file_paths); |
|
686 | - // if loading failed, or we are only loading a file but NOT instantiating an object |
|
687 | - if ( ! $loaded || $load_only) { |
|
688 | - // return boolean if only loading, or null if an object was expected |
|
689 | - return $load_only ? $loaded : null; |
|
690 | - } |
|
691 | - } |
|
692 | - // instantiate the requested object |
|
693 | - $class_obj = $this->_create_object($class_name, $arguments, $type, $from_db); |
|
694 | - if ($this->_cache_on && $cache) { |
|
695 | - // save it for later... kinda like gum { : $ |
|
696 | - $this->_set_cached_class($class_obj, $class_name, $class_prefix, $from_db); |
|
697 | - } |
|
698 | - $this->_cache_on = true; |
|
699 | - return $class_obj; |
|
700 | - } |
|
701 | - |
|
702 | - |
|
703 | - |
|
704 | - |
|
705 | - /** |
|
706 | - * _get_cached_class |
|
707 | - * attempts to find a cached version of the requested class |
|
708 | - * by looking in the following places: |
|
709 | - * $this->{$class_abbreviation} ie: $this->CART |
|
710 | - * $this->{$class_name} ie: $this->Some_Class |
|
711 | - * $this->LIB->{$class_name} ie: $this->LIB->Some_Class |
|
712 | - * $this->addon->{$class_name} ie: $this->addon->Some_Addon_Class |
|
713 | - * |
|
714 | - * @access protected |
|
715 | - * @param string $class_name |
|
716 | - * @param string $class_prefix |
|
717 | - * @return mixed |
|
718 | - */ |
|
719 | - protected function _get_cached_class($class_name, $class_prefix = '') |
|
720 | - { |
|
721 | - if ($class_name === 'EE_Registry') { |
|
722 | - return $this; |
|
723 | - } |
|
724 | - // have to specify something, but not anything that will conflict |
|
725 | - $class_abbreviation = isset($this->_class_abbreviations[ $class_name ]) |
|
726 | - ? $this->_class_abbreviations[ $class_name ] |
|
727 | - : 'FANCY_BATMAN_PANTS'; |
|
728 | - $class_name = str_replace('\\', '_', $class_name); |
|
729 | - // check if class has already been loaded, and return it if it has been |
|
730 | - if (isset($this->{$class_abbreviation}) && ! is_null($this->{$class_abbreviation})) { |
|
731 | - return $this->{$class_abbreviation}; |
|
732 | - } |
|
733 | - if (isset ($this->{$class_name})) { |
|
734 | - return $this->{$class_name}; |
|
735 | - } |
|
736 | - if (isset ($this->LIB->{$class_name})) { |
|
737 | - return $this->LIB->{$class_name}; |
|
738 | - } |
|
739 | - if ($class_prefix === 'addon' && isset ($this->addons->{$class_name})) { |
|
740 | - return $this->addons->{$class_name}; |
|
741 | - } |
|
742 | - return null; |
|
743 | - } |
|
744 | - |
|
745 | - |
|
746 | - |
|
747 | - /** |
|
748 | - * removes a cached version of the requested class |
|
749 | - * |
|
750 | - * @param string $class_name |
|
751 | - * @param boolean $addon |
|
752 | - * @return boolean |
|
753 | - */ |
|
754 | - public function clear_cached_class($class_name, $addon = false) |
|
755 | - { |
|
756 | - // have to specify something, but not anything that will conflict |
|
757 | - $class_abbreviation = isset($this->_class_abbreviations[ $class_name ]) |
|
758 | - ? $this->_class_abbreviations[ $class_name ] |
|
759 | - : 'FANCY_BATMAN_PANTS'; |
|
760 | - $class_name = str_replace('\\', '_', $class_name); |
|
761 | - // check if class has already been loaded, and return it if it has been |
|
762 | - if (isset($this->{$class_abbreviation}) && ! is_null($this->{$class_abbreviation})) { |
|
763 | - $this->{$class_abbreviation} = null; |
|
764 | - return true; |
|
765 | - } |
|
766 | - if (isset($this->{$class_name})) { |
|
767 | - $this->{$class_name} = null; |
|
768 | - return true; |
|
769 | - } |
|
770 | - if (isset($this->LIB->{$class_name})) { |
|
771 | - unset($this->LIB->{$class_name}); |
|
772 | - return true; |
|
773 | - } |
|
774 | - if ($addon && isset($this->addons->{$class_name})) { |
|
775 | - unset($this->addons->{$class_name}); |
|
776 | - return true; |
|
777 | - } |
|
778 | - return false; |
|
779 | - } |
|
780 | - |
|
781 | - |
|
782 | - /** |
|
783 | - * _resolve_path |
|
784 | - * attempts to find a full valid filepath for the requested class. |
|
785 | - * loops thru each of the base paths in the $file_paths array and appends : "{classname} . {file type} . php" |
|
786 | - * then returns that path if the target file has been found and is readable |
|
787 | - * |
|
788 | - * @access protected |
|
789 | - * @param string $class_name |
|
790 | - * @param string $type |
|
791 | - * @param array $file_paths |
|
792 | - * @return string | bool |
|
793 | - */ |
|
794 | - protected function _resolve_path($class_name, $type = '', $file_paths = array()) |
|
795 | - { |
|
796 | - // make sure $file_paths is an array |
|
797 | - $file_paths = is_array($file_paths) ? $file_paths : array($file_paths); |
|
798 | - // cycle thru paths |
|
799 | - foreach ($file_paths as $key => $file_path) { |
|
800 | - // convert all separators to proper DS, if no filepath, then use EE_CLASSES |
|
801 | - $file_path = $file_path ? str_replace(array('/', '\\'), DS, $file_path) : EE_CLASSES; |
|
802 | - // prep file type |
|
803 | - $type = ! empty($type) ? trim($type, '.') . '.' : ''; |
|
804 | - // build full file path |
|
805 | - $file_paths[$key] = rtrim($file_path, DS) . DS . $class_name . '.' . $type . 'php'; |
|
806 | - //does the file exist and can be read ? |
|
807 | - if (is_readable($file_paths[$key])) { |
|
808 | - return $file_paths[$key]; |
|
809 | - } |
|
810 | - } |
|
811 | - return false; |
|
812 | - } |
|
813 | - |
|
814 | - |
|
815 | - |
|
816 | - /** |
|
817 | - * _require_file |
|
818 | - * basically just performs a require_once() |
|
819 | - * but with some error handling |
|
820 | - * |
|
821 | - * @access protected |
|
822 | - * @param string $path |
|
823 | - * @param string $class_name |
|
824 | - * @param string $type |
|
825 | - * @param array $file_paths |
|
826 | - * @return boolean |
|
827 | - * @throws \EE_Error |
|
828 | - */ |
|
829 | - protected function _require_file($path, $class_name, $type = '', $file_paths = array()) |
|
830 | - { |
|
831 | - $this->resolve_legacy_class_parent($class_name); |
|
832 | - // don't give up! you gotta... |
|
833 | - try { |
|
834 | - //does the file exist and can it be read ? |
|
835 | - if ( ! $path) { |
|
836 | - // so sorry, can't find the file |
|
837 | - throw new EE_Error ( |
|
838 | - sprintf( |
|
839 | - __('The %1$s file %2$s could not be located or is not readable due to file permissions. Please ensure that the following filepath(s) are correct: %3$s', 'event_espresso'), |
|
840 | - trim($type, '.'), |
|
841 | - $class_name, |
|
842 | - '<br />' . implode(',<br />', $file_paths) |
|
843 | - ) |
|
844 | - ); |
|
845 | - } |
|
846 | - // get the file |
|
847 | - require_once($path); |
|
848 | - // if the class isn't already declared somewhere |
|
849 | - if (class_exists($class_name, false) === false) { |
|
850 | - // so sorry, not a class |
|
851 | - throw new EE_Error( |
|
852 | - sprintf( |
|
853 | - __('The %s file %s does not appear to contain the %s Class.', 'event_espresso'), |
|
854 | - $type, |
|
855 | - $path, |
|
856 | - $class_name |
|
857 | - ) |
|
858 | - ); |
|
859 | - } |
|
860 | - } catch (EE_Error $e) { |
|
861 | - $e->get_error(); |
|
862 | - return false; |
|
863 | - } |
|
864 | - return true; |
|
865 | - } |
|
866 | - |
|
867 | - |
|
868 | - |
|
869 | - /** |
|
870 | - * Some of our legacy classes that extended a parent class would simply use a require() statement |
|
871 | - * before their class declaration in order to ensure that the parent class was loaded. |
|
872 | - * This is not ideal, but it's nearly impossible to determine the parent class of a non-namespaced class, |
|
873 | - * without triggering a fatal error because the parent class has yet to be loaded and therefore doesn't exist. |
|
874 | - * |
|
875 | - * @param string $class_name |
|
876 | - */ |
|
877 | - protected function resolve_legacy_class_parent($class_name = '') |
|
878 | - { |
|
879 | - try { |
|
880 | - $legacy_parent_class_map = array( |
|
881 | - 'EE_Payment_Processor' => 'core/business/EE_Processor_Base.class.php' |
|
882 | - ); |
|
883 | - if(isset($legacy_parent_class_map[$class_name])) { |
|
884 | - require_once EE_PLUGIN_DIR_PATH . $legacy_parent_class_map[$class_name]; |
|
885 | - } |
|
886 | - } catch (Exception $exception) { |
|
887 | - } |
|
888 | - } |
|
889 | - |
|
890 | - |
|
891 | - |
|
892 | - /** |
|
893 | - * _create_object |
|
894 | - * Attempts to instantiate the requested class via any of the |
|
895 | - * commonly used instantiation methods employed throughout EE. |
|
896 | - * The priority for instantiation is as follows: |
|
897 | - * - abstract classes or any class flagged as "load only" (no instantiation occurs) |
|
898 | - * - model objects via their 'new_instance_from_db' method |
|
899 | - * - model objects via their 'new_instance' method |
|
900 | - * - "singleton" classes" via their 'instance' method |
|
901 | - * - standard instantiable classes via their __constructor |
|
902 | - * Prior to instantiation, if the classname exists in the dependency_map, |
|
903 | - * then the constructor for the requested class will be examined to determine |
|
904 | - * if any dependencies exist, and if they can be injected. |
|
905 | - * If so, then those classes will be added to the array of arguments passed to the constructor |
|
906 | - * |
|
907 | - * @access protected |
|
908 | - * @param string $class_name |
|
909 | - * @param array $arguments |
|
910 | - * @param string $type |
|
911 | - * @param bool $from_db |
|
912 | - * @return null | object |
|
913 | - * @throws \EE_Error |
|
914 | - */ |
|
915 | - protected function _create_object($class_name, $arguments = array(), $type = '', $from_db = false) |
|
916 | - { |
|
917 | - $class_obj = null; |
|
918 | - $instantiation_mode = '0) none'; |
|
919 | - // don't give up! you gotta... |
|
920 | - try { |
|
921 | - // create reflection |
|
922 | - $reflector = $this->get_ReflectionClass($class_name); |
|
923 | - // make sure arguments are an array |
|
924 | - $arguments = is_array($arguments) ? $arguments : array($arguments); |
|
925 | - // and if arguments array is numerically and sequentially indexed, then we want it to remain as is, |
|
926 | - // else wrap it in an additional array so that it doesn't get split into multiple parameters |
|
927 | - $arguments = $this->_array_is_numerically_and_sequentially_indexed($arguments) |
|
928 | - ? $arguments |
|
929 | - : array($arguments); |
|
930 | - // attempt to inject dependencies ? |
|
931 | - if ($this->_dependency_map->has($class_name)) { |
|
932 | - $arguments = $this->_resolve_dependencies($reflector, $class_name, $arguments); |
|
933 | - } |
|
934 | - // instantiate the class if possible |
|
935 | - if ($reflector->isAbstract()) { |
|
936 | - // nothing to instantiate, loading file was enough |
|
937 | - // does not throw an exception so $instantiation_mode is unused |
|
938 | - // $instantiation_mode = "1) no constructor abstract class"; |
|
939 | - $class_obj = true; |
|
940 | - } else if ($reflector->getConstructor() === null && $reflector->isInstantiable() && empty($arguments)) { |
|
941 | - // no constructor = static methods only... nothing to instantiate, loading file was enough |
|
942 | - $instantiation_mode = "2) no constructor but instantiable"; |
|
943 | - $class_obj = $reflector->newInstance(); |
|
944 | - } else if ($from_db && method_exists($class_name, 'new_instance_from_db')) { |
|
945 | - $instantiation_mode = "3) new_instance_from_db()"; |
|
946 | - $class_obj = call_user_func_array(array($class_name, 'new_instance_from_db'), $arguments); |
|
947 | - } else if (method_exists($class_name, 'new_instance')) { |
|
948 | - $instantiation_mode = "4) new_instance()"; |
|
949 | - $class_obj = call_user_func_array(array($class_name, 'new_instance'), $arguments); |
|
950 | - } else if (method_exists($class_name, 'instance')) { |
|
951 | - $instantiation_mode = "5) instance()"; |
|
952 | - $class_obj = call_user_func_array(array($class_name, 'instance'), $arguments); |
|
953 | - } else if ($reflector->isInstantiable()) { |
|
954 | - $instantiation_mode = "6) constructor"; |
|
955 | - $class_obj = $reflector->newInstanceArgs($arguments); |
|
956 | - } else { |
|
957 | - // heh ? something's not right ! |
|
958 | - throw new EE_Error( |
|
959 | - sprintf( |
|
960 | - __('The %s file %s could not be instantiated.', 'event_espresso'), |
|
961 | - $type, |
|
962 | - $class_name |
|
963 | - ) |
|
964 | - ); |
|
965 | - } |
|
966 | - } catch (Exception $e) { |
|
967 | - if ( ! $e instanceof EE_Error) { |
|
968 | - $e = new EE_Error( |
|
969 | - sprintf( |
|
970 | - __('The following error occurred while attempting to instantiate "%1$s": %2$s %3$s %2$s instantiation mode : %4$s', 'event_espresso'), |
|
971 | - $class_name, |
|
972 | - '<br />', |
|
973 | - $e->getMessage(), |
|
974 | - $instantiation_mode |
|
975 | - ) |
|
976 | - ); |
|
977 | - } |
|
978 | - $e->get_error(); |
|
979 | - } |
|
980 | - return $class_obj; |
|
981 | - } |
|
982 | - |
|
983 | - |
|
984 | - |
|
985 | - /** |
|
986 | - * @see http://stackoverflow.com/questions/173400/how-to-check-if-php-array-is-associative-or-sequential |
|
987 | - * @param array $array |
|
988 | - * @return bool |
|
989 | - */ |
|
990 | - protected function _array_is_numerically_and_sequentially_indexed(array $array) |
|
991 | - { |
|
992 | - return ! empty($array) ? array_keys($array) === range(0, count($array) - 1) : true; |
|
993 | - } |
|
994 | - |
|
995 | - |
|
996 | - |
|
997 | - /** |
|
998 | - * getReflectionClass |
|
999 | - * checks if a ReflectionClass object has already been generated for a class |
|
1000 | - * and returns that instead of creating a new one |
|
1001 | - * |
|
1002 | - * @access public |
|
1003 | - * @param string $class_name |
|
1004 | - * @return ReflectionClass |
|
1005 | - */ |
|
1006 | - public function get_ReflectionClass($class_name) |
|
1007 | - { |
|
1008 | - if ( |
|
1009 | - ! isset($this->_reflectors[$class_name]) |
|
1010 | - || ! $this->_reflectors[$class_name] instanceof ReflectionClass |
|
1011 | - ) { |
|
1012 | - $this->_reflectors[$class_name] = new ReflectionClass($class_name); |
|
1013 | - } |
|
1014 | - return $this->_reflectors[$class_name]; |
|
1015 | - } |
|
1016 | - |
|
1017 | - |
|
1018 | - |
|
1019 | - /** |
|
1020 | - * _resolve_dependencies |
|
1021 | - * examines the constructor for the requested class to determine |
|
1022 | - * if any dependencies exist, and if they can be injected. |
|
1023 | - * If so, then those classes will be added to the array of arguments passed to the constructor |
|
1024 | - * PLZ NOTE: this is achieved by type hinting the constructor params |
|
1025 | - * For example: |
|
1026 | - * if attempting to load a class "Foo" with the following constructor: |
|
1027 | - * __construct( Bar $bar_class, Fighter $grohl_class ) |
|
1028 | - * then $bar_class and $grohl_class will be added to the $arguments array, |
|
1029 | - * but only IF they are NOT already present in the incoming arguments array, |
|
1030 | - * and the correct classes can be loaded |
|
1031 | - * |
|
1032 | - * @access protected |
|
1033 | - * @param ReflectionClass $reflector |
|
1034 | - * @param string $class_name |
|
1035 | - * @param array $arguments |
|
1036 | - * @return array |
|
1037 | - * @throws \ReflectionException |
|
1038 | - */ |
|
1039 | - protected function _resolve_dependencies(ReflectionClass $reflector, $class_name, $arguments = array()) |
|
1040 | - { |
|
1041 | - // let's examine the constructor |
|
1042 | - $constructor = $reflector->getConstructor(); |
|
1043 | - // whu? huh? nothing? |
|
1044 | - if ( ! $constructor) { |
|
1045 | - return $arguments; |
|
1046 | - } |
|
1047 | - // get constructor parameters |
|
1048 | - $params = $constructor->getParameters(); |
|
1049 | - // and the keys for the incoming arguments array so that we can compare existing arguments with what is expected |
|
1050 | - $argument_keys = array_keys($arguments); |
|
1051 | - // now loop thru all of the constructors expected parameters |
|
1052 | - foreach ($params as $index => $param) { |
|
1053 | - // is this a dependency for a specific class ? |
|
1054 | - $param_class = $param->getClass() ? $param->getClass()->name : null; |
|
1055 | - // BUT WAIT !!! This class may be an alias for something else (or getting replaced at runtime) |
|
1056 | - $param_class = $this->_dependency_map->has_alias($param_class, $class_name) |
|
1057 | - ? $this->_dependency_map->get_alias($param_class, $class_name) |
|
1058 | - : $param_class; |
|
1059 | - if ( |
|
1060 | - // param is not even a class |
|
1061 | - empty($param_class) |
|
1062 | - // and something already exists in the incoming arguments for this param |
|
1063 | - && isset($argument_keys[$index], $arguments[$argument_keys[$index]]) |
|
1064 | - ) { |
|
1065 | - // so let's skip this argument and move on to the next |
|
1066 | - continue; |
|
1067 | - } |
|
1068 | - if ( |
|
1069 | - // parameter is type hinted as a class, exists as an incoming argument, AND it's the correct class |
|
1070 | - ! empty($param_class) |
|
1071 | - && isset($argument_keys[$index], $arguments[$argument_keys[$index]]) |
|
1072 | - && $arguments[$argument_keys[$index]] instanceof $param_class |
|
1073 | - ) { |
|
1074 | - // skip this argument and move on to the next |
|
1075 | - continue; |
|
1076 | - } |
|
1077 | - if ( |
|
1078 | - // parameter is type hinted as a class, and should be injected |
|
1079 | - ! empty($param_class) |
|
1080 | - && $this->_dependency_map->has_dependency_for_class($class_name, $param_class) |
|
1081 | - ) { |
|
1082 | - $arguments = $this->_resolve_dependency($class_name, $param_class, $arguments, $index); |
|
1083 | - } else { |
|
1084 | - try { |
|
1085 | - $arguments[$index] = $param->getDefaultValue(); |
|
1086 | - } catch (ReflectionException $e) { |
|
1087 | - throw new ReflectionException( |
|
1088 | - sprintf( |
|
1089 | - __('%1$s for parameter "$%2$s"', 'event_espresso'), |
|
1090 | - $e->getMessage(), |
|
1091 | - $param->getName() |
|
1092 | - ) |
|
1093 | - ); |
|
1094 | - } |
|
1095 | - } |
|
1096 | - } |
|
1097 | - return $arguments; |
|
1098 | - } |
|
1099 | - |
|
1100 | - |
|
1101 | - |
|
1102 | - /** |
|
1103 | - * @access protected |
|
1104 | - * @param string $class_name |
|
1105 | - * @param string $param_class |
|
1106 | - * @param array $arguments |
|
1107 | - * @param mixed $index |
|
1108 | - * @return array |
|
1109 | - */ |
|
1110 | - protected function _resolve_dependency($class_name, $param_class, $arguments, $index) |
|
1111 | - { |
|
1112 | - $dependency = null; |
|
1113 | - // should dependency be loaded from cache ? |
|
1114 | - $cache_on = $this->_dependency_map->loading_strategy_for_class_dependency($class_name, $param_class) |
|
1115 | - !== EE_Dependency_Map::load_new_object |
|
1116 | - ? true |
|
1117 | - : false; |
|
1118 | - // we might have a dependency... |
|
1119 | - // let's MAYBE try and find it in our cache if that's what's been requested |
|
1120 | - $cached_class = $cache_on ? $this->_get_cached_class($param_class) : null; |
|
1121 | - // and grab it if it exists |
|
1122 | - if ($cached_class instanceof $param_class) { |
|
1123 | - $dependency = $cached_class; |
|
1124 | - } else if ($param_class !== $class_name) { |
|
1125 | - // obtain the loader method from the dependency map |
|
1126 | - $loader = $this->_dependency_map->class_loader($param_class); |
|
1127 | - // is loader a custom closure ? |
|
1128 | - if ($loader instanceof Closure) { |
|
1129 | - $dependency = $loader(); |
|
1130 | - } else { |
|
1131 | - // set the cache on property for the recursive loading call |
|
1132 | - $this->_cache_on = $cache_on; |
|
1133 | - // if not, then let's try and load it via the registry |
|
1134 | - if ($loader && method_exists($this, $loader)) { |
|
1135 | - $dependency = $this->{$loader}($param_class); |
|
1136 | - } else { |
|
1137 | - $dependency = $this->create($param_class, array(), $cache_on); |
|
1138 | - } |
|
1139 | - } |
|
1140 | - } |
|
1141 | - // did we successfully find the correct dependency ? |
|
1142 | - if ($dependency instanceof $param_class) { |
|
1143 | - // then let's inject it into the incoming array of arguments at the correct location |
|
1144 | - if (isset($argument_keys[$index])) { |
|
1145 | - $arguments[$argument_keys[$index]] = $dependency; |
|
1146 | - } else { |
|
1147 | - $arguments[$index] = $dependency; |
|
1148 | - } |
|
1149 | - } |
|
1150 | - return $arguments; |
|
1151 | - } |
|
1152 | - |
|
1153 | - |
|
1154 | - |
|
1155 | - /** |
|
1156 | - * _set_cached_class |
|
1157 | - * attempts to cache the instantiated class locally |
|
1158 | - * in one of the following places, in the following order: |
|
1159 | - * $this->{class_abbreviation} ie: $this->CART |
|
1160 | - * $this->{$class_name} ie: $this->Some_Class |
|
1161 | - * $this->addon->{$$class_name} ie: $this->addon->Some_Addon_Class |
|
1162 | - * $this->LIB->{$class_name} ie: $this->LIB->Some_Class |
|
1163 | - * |
|
1164 | - * @access protected |
|
1165 | - * @param object $class_obj |
|
1166 | - * @param string $class_name |
|
1167 | - * @param string $class_prefix |
|
1168 | - * @param bool $from_db |
|
1169 | - * @return void |
|
1170 | - */ |
|
1171 | - protected function _set_cached_class($class_obj, $class_name, $class_prefix = '', $from_db = false) |
|
1172 | - { |
|
1173 | - if ($class_name === 'EE_Registry' || empty($class_obj)) { |
|
1174 | - return; |
|
1175 | - } |
|
1176 | - // return newly instantiated class |
|
1177 | - if (isset($this->_class_abbreviations[$class_name])) { |
|
1178 | - $class_abbreviation = $this->_class_abbreviations[$class_name]; |
|
1179 | - $this->{$class_abbreviation} = $class_obj; |
|
1180 | - return; |
|
1181 | - } |
|
1182 | - $class_name = str_replace('\\', '_', $class_name); |
|
1183 | - if (property_exists($this, $class_name)) { |
|
1184 | - $this->{$class_name} = $class_obj; |
|
1185 | - return; |
|
1186 | - } |
|
1187 | - if ($class_prefix === 'addon') { |
|
1188 | - $this->addons->{$class_name} = $class_obj; |
|
1189 | - return; |
|
1190 | - } |
|
1191 | - if ( ! $from_db) { |
|
1192 | - $this->LIB->{$class_name} = $class_obj; |
|
1193 | - } |
|
1194 | - } |
|
1195 | - |
|
1196 | - |
|
1197 | - |
|
1198 | - /** |
|
1199 | - * call any loader that's been registered in the EE_Dependency_Map::$_class_loaders array |
|
1200 | - * |
|
1201 | - * @param string $classname PLEASE NOTE: the class name needs to match what's registered |
|
1202 | - * in the EE_Dependency_Map::$_class_loaders array, |
|
1203 | - * including the class prefix, ie: "EE_", "EEM_", "EEH_", etc |
|
1204 | - * @param array $arguments |
|
1205 | - * @return object |
|
1206 | - */ |
|
1207 | - public static function factory($classname, $arguments = array()) |
|
1208 | - { |
|
1209 | - $loader = self::instance()->_dependency_map->class_loader($classname); |
|
1210 | - if ($loader instanceof Closure) { |
|
1211 | - return $loader($arguments); |
|
1212 | - } |
|
1213 | - if (method_exists(EE_Registry::instance(), $loader)) { |
|
1214 | - return EE_Registry::instance()->{$loader}($classname, $arguments); |
|
1215 | - } |
|
1216 | - return null; |
|
1217 | - } |
|
1218 | - |
|
1219 | - |
|
1220 | - |
|
1221 | - /** |
|
1222 | - * Gets the addon by its name/slug (not classname. For that, just |
|
1223 | - * use the classname as the property name on EE_Config::instance()->addons) |
|
1224 | - * |
|
1225 | - * @param string $name |
|
1226 | - * @return EE_Addon |
|
1227 | - */ |
|
1228 | - public function get_addon_by_name($name) |
|
1229 | - { |
|
1230 | - foreach ($this->addons as $addon) { |
|
1231 | - if ($addon->name() == $name) { |
|
1232 | - return $addon; |
|
1233 | - } |
|
1234 | - } |
|
1235 | - return null; |
|
1236 | - } |
|
1237 | - |
|
1238 | - |
|
1239 | - |
|
1240 | - /** |
|
1241 | - * Gets an array of all the registered addons, where the keys are their names. (ie, what each returns for their name() function) They're already available on EE_Config::instance()->addons as properties, where each property's name is |
|
1242 | - * the addon's classname. So if you just want to get the addon by classname, use EE_Config::instance()->addons->{classname} |
|
1243 | - * |
|
1244 | - * @return EE_Addon[] where the KEYS are the addon's name() |
|
1245 | - */ |
|
1246 | - public function get_addons_by_name() |
|
1247 | - { |
|
1248 | - $addons = array(); |
|
1249 | - foreach ($this->addons as $addon) { |
|
1250 | - $addons[$addon->name()] = $addon; |
|
1251 | - } |
|
1252 | - return $addons; |
|
1253 | - } |
|
1254 | - |
|
1255 | - |
|
1256 | - |
|
1257 | - /** |
|
1258 | - * Resets the specified model's instance AND makes sure EE_Registry doesn't keep |
|
1259 | - * a stale copy of it around |
|
1260 | - * |
|
1261 | - * @param string $model_name |
|
1262 | - * @return \EEM_Base |
|
1263 | - * @throws \EE_Error |
|
1264 | - */ |
|
1265 | - public function reset_model($model_name) |
|
1266 | - { |
|
1267 | - $model_class_name = strpos($model_name, 'EEM_') !== 0 ? "EEM_{$model_name}" : $model_name; |
|
1268 | - if ( ! isset($this->LIB->{$model_class_name}) || ! $this->LIB->{$model_class_name} instanceof EEM_Base) { |
|
1269 | - return null; |
|
1270 | - } |
|
1271 | - //get that model reset it and make sure we nuke the old reference to it |
|
1272 | - if ($this->LIB->{$model_class_name} instanceof $model_class_name && is_callable(array($model_class_name, 'reset'))) { |
|
1273 | - $this->LIB->{$model_class_name} = $this->LIB->{$model_class_name}->reset(); |
|
1274 | - } else { |
|
1275 | - throw new EE_Error(sprintf(__('Model %s does not have a method "reset"', 'event_espresso'), $model_name)); |
|
1276 | - } |
|
1277 | - return $this->LIB->{$model_class_name}; |
|
1278 | - } |
|
1279 | - |
|
1280 | - |
|
1281 | - |
|
1282 | - /** |
|
1283 | - * Resets the registry. |
|
1284 | - * The criteria for what gets reset is based on what can be shared between sites on the same request when switch_to_blog |
|
1285 | - * is used in a multisite install. Here is a list of things that are NOT reset. |
|
1286 | - * - $_dependency_map |
|
1287 | - * - $_class_abbreviations |
|
1288 | - * - $NET_CFG (EE_Network_Config): The config is shared network wide so no need to reset. |
|
1289 | - * - $REQ: Still on the same request so no need to change. |
|
1290 | - * - $CAP: There is no site specific state in the EE_Capability class. |
|
1291 | - * - $SSN: Although ideally, the session should not be shared between site switches, we can't reset it because only one Session |
|
1292 | - * can be active in a single request. Resetting could resolve in "headers already sent" errors. |
|
1293 | - * - $addons: In multisite, the state of the addons is something controlled via hooks etc in a normal request. So |
|
1294 | - * for now, we won't reset the addons because it could break calls to an add-ons class/methods in the |
|
1295 | - * switch or on the restore. |
|
1296 | - * - $modules |
|
1297 | - * - $shortcodes |
|
1298 | - * - $widgets |
|
1299 | - * |
|
1300 | - * @param boolean $hard whether to reset data in the database too, or just refresh |
|
1301 | - * the Registry to its state at the beginning of the request |
|
1302 | - * @param boolean $reinstantiate whether to create new instances of EE_Registry's singletons too, |
|
1303 | - * or just reset without re-instantiating (handy to set to FALSE if you're not sure if you CAN |
|
1304 | - * currently reinstantiate the singletons at the moment) |
|
1305 | - * @param bool $reset_models Defaults to true. When false, then the models are not reset. This is so client |
|
1306 | - * code instead can just change the model context to a different blog id if necessary |
|
1307 | - * @return EE_Registry |
|
1308 | - */ |
|
1309 | - public static function reset($hard = false, $reinstantiate = true, $reset_models = true) |
|
1310 | - { |
|
1311 | - $instance = self::instance(); |
|
1312 | - $instance->_cache_on = true; |
|
1313 | - // reset some "special" classes |
|
1314 | - EEH_Activation::reset(); |
|
1315 | - $instance->CFG = $instance->CFG->reset($hard, $reinstantiate); |
|
1316 | - $instance->CART = null; |
|
1317 | - $instance->MRM = null; |
|
1318 | - $instance->AssetsRegistry = null; |
|
1319 | - $instance->AssetsRegistry = $instance->create('EventEspresso\core\services\assets\Registry'); |
|
1320 | - //messages reset |
|
1321 | - EED_Messages::reset(); |
|
1322 | - //handle of objects cached on LIB |
|
1323 | - foreach (array('LIB', 'modules', 'shortcodes') as $cache) { |
|
1324 | - foreach ($instance->{$cache} as $class_name => $class) { |
|
1325 | - if (EE_Registry::_reset_and_unset_object($class, $reset_models)) { |
|
1326 | - unset($instance->{$cache}->{$class_name}); |
|
1327 | - } |
|
1328 | - } |
|
1329 | - } |
|
1330 | - return $instance; |
|
1331 | - } |
|
1332 | - |
|
1333 | - |
|
1334 | - |
|
1335 | - /** |
|
1336 | - * if passed object implements ResettableInterface, then call it's reset() method |
|
1337 | - * if passed object implements InterminableInterface, then return false, |
|
1338 | - * to indicate that it should NOT be cleared from the Registry cache |
|
1339 | - * |
|
1340 | - * @param $object |
|
1341 | - * @param bool $reset_models |
|
1342 | - * @return bool returns true if cached object should be unset |
|
1343 | - */ |
|
1344 | - private static function _reset_and_unset_object($object, $reset_models) |
|
1345 | - { |
|
1346 | - static $count = 0; |
|
1347 | - $count++; |
|
1348 | - if ($object instanceof ResettableInterface) { |
|
1349 | - if ($object instanceof EEM_Base) { |
|
1350 | - if ($reset_models) { |
|
1351 | - $object->reset(); |
|
1352 | - return true; |
|
1353 | - } |
|
1354 | - return false; |
|
1355 | - } |
|
1356 | - $object->reset(); |
|
1357 | - return true; |
|
1358 | - } |
|
1359 | - if ( ! $object instanceof InterminableInterface) { |
|
1360 | - return true; |
|
1361 | - } |
|
1362 | - return false; |
|
1363 | - } |
|
1364 | - |
|
1365 | - |
|
1366 | - |
|
1367 | - /** |
|
1368 | - * @override magic methods |
|
1369 | - * @return void |
|
1370 | - */ |
|
1371 | - public final function __destruct() |
|
1372 | - { |
|
1373 | - } |
|
1374 | - |
|
1375 | - |
|
1376 | - |
|
1377 | - /** |
|
1378 | - * @param $a |
|
1379 | - * @param $b |
|
1380 | - */ |
|
1381 | - public final function __call($a, $b) |
|
1382 | - { |
|
1383 | - } |
|
1384 | - |
|
1385 | - |
|
1386 | - |
|
1387 | - /** |
|
1388 | - * @param $a |
|
1389 | - */ |
|
1390 | - public final function __get($a) |
|
1391 | - { |
|
1392 | - } |
|
1393 | - |
|
1394 | - |
|
1395 | - |
|
1396 | - /** |
|
1397 | - * @param $a |
|
1398 | - * @param $b |
|
1399 | - */ |
|
1400 | - public final function __set($a, $b) |
|
1401 | - { |
|
1402 | - } |
|
1403 | - |
|
1404 | - |
|
1405 | - |
|
1406 | - /** |
|
1407 | - * @param $a |
|
1408 | - */ |
|
1409 | - public final function __isset($a) |
|
1410 | - { |
|
1411 | - } |
|
22 | + /** |
|
23 | + * EE_Registry Object |
|
24 | + * |
|
25 | + * @var EE_Registry $_instance |
|
26 | + * @access private |
|
27 | + */ |
|
28 | + private static $_instance = null; |
|
29 | + |
|
30 | + /** |
|
31 | + * @var EE_Dependency_Map $_dependency_map |
|
32 | + * @access protected |
|
33 | + */ |
|
34 | + protected $_dependency_map = null; |
|
35 | + |
|
36 | + /** |
|
37 | + * @var array $_class_abbreviations |
|
38 | + * @access protected |
|
39 | + */ |
|
40 | + protected $_class_abbreviations = array(); |
|
41 | + |
|
42 | + /** |
|
43 | + * @access public |
|
44 | + * @var \EventEspresso\core\services\commands\CommandBusInterface $BUS |
|
45 | + */ |
|
46 | + public $BUS; |
|
47 | + |
|
48 | + /** |
|
49 | + * EE_Cart Object |
|
50 | + * |
|
51 | + * @access public |
|
52 | + * @var EE_Cart $CART |
|
53 | + */ |
|
54 | + public $CART = null; |
|
55 | + |
|
56 | + /** |
|
57 | + * EE_Config Object |
|
58 | + * |
|
59 | + * @access public |
|
60 | + * @var EE_Config $CFG |
|
61 | + */ |
|
62 | + public $CFG = null; |
|
63 | + |
|
64 | + /** |
|
65 | + * EE_Network_Config Object |
|
66 | + * |
|
67 | + * @access public |
|
68 | + * @var EE_Network_Config $NET_CFG |
|
69 | + */ |
|
70 | + public $NET_CFG = null; |
|
71 | + |
|
72 | + /** |
|
73 | + * StdClass object for storing library classes in |
|
74 | + * |
|
75 | + * @public LIB |
|
76 | + * @var StdClass $LIB |
|
77 | + */ |
|
78 | + public $LIB = null; |
|
79 | + |
|
80 | + /** |
|
81 | + * EE_Request_Handler Object |
|
82 | + * |
|
83 | + * @access public |
|
84 | + * @var EE_Request_Handler $REQ |
|
85 | + */ |
|
86 | + public $REQ = null; |
|
87 | + |
|
88 | + /** |
|
89 | + * EE_Session Object |
|
90 | + * |
|
91 | + * @access public |
|
92 | + * @var EE_Session $SSN |
|
93 | + */ |
|
94 | + public $SSN = null; |
|
95 | + |
|
96 | + /** |
|
97 | + * holds the ee capabilities object. |
|
98 | + * |
|
99 | + * @since 4.5.0 |
|
100 | + * @var EE_Capabilities |
|
101 | + */ |
|
102 | + public $CAP = null; |
|
103 | + |
|
104 | + /** |
|
105 | + * holds the EE_Message_Resource_Manager object. |
|
106 | + * |
|
107 | + * @since 4.9.0 |
|
108 | + * @var EE_Message_Resource_Manager |
|
109 | + */ |
|
110 | + public $MRM = null; |
|
111 | + |
|
112 | + |
|
113 | + /** |
|
114 | + * Holds the Assets Registry instance |
|
115 | + * @var Registry |
|
116 | + */ |
|
117 | + public $AssetsRegistry = null; |
|
118 | + |
|
119 | + /** |
|
120 | + * $addons - StdClass object for holding addons which have registered themselves to work with EE core |
|
121 | + * |
|
122 | + * @access public |
|
123 | + * @var EE_Addon[] |
|
124 | + */ |
|
125 | + public $addons = null; |
|
126 | + |
|
127 | + /** |
|
128 | + * $models |
|
129 | + * @access public |
|
130 | + * @var EEM_Base[] $models keys are 'short names' (eg Event), values are class names (eg 'EEM_Event') |
|
131 | + */ |
|
132 | + public $models = array(); |
|
133 | + |
|
134 | + /** |
|
135 | + * $modules |
|
136 | + * @access public |
|
137 | + * @var EED_Module[] $modules |
|
138 | + */ |
|
139 | + public $modules = null; |
|
140 | + |
|
141 | + /** |
|
142 | + * $shortcodes |
|
143 | + * @access public |
|
144 | + * @var EES_Shortcode[] $shortcodes |
|
145 | + */ |
|
146 | + public $shortcodes = null; |
|
147 | + |
|
148 | + /** |
|
149 | + * $widgets |
|
150 | + * @access public |
|
151 | + * @var WP_Widget[] $widgets |
|
152 | + */ |
|
153 | + public $widgets = null; |
|
154 | + |
|
155 | + /** |
|
156 | + * $non_abstract_db_models |
|
157 | + * @access public |
|
158 | + * @var array this is an array of all implemented model names (i.e. not the parent abstract models, or models |
|
159 | + * which don't actually fetch items from the DB in the normal way (ie, are not children of EEM_Base)). |
|
160 | + * Keys are model "short names" (eg "Event") as used in model relations, and values are |
|
161 | + * classnames (eg "EEM_Event") |
|
162 | + */ |
|
163 | + public $non_abstract_db_models = array(); |
|
164 | + |
|
165 | + |
|
166 | + /** |
|
167 | + * $i18n_js_strings - internationalization for JS strings |
|
168 | + * usage: EE_Registry::i18n_js_strings['string_key'] = __( 'string to translate.', 'event_espresso' ); |
|
169 | + * in js file: var translatedString = eei18n.string_key; |
|
170 | + * |
|
171 | + * @access public |
|
172 | + * @var array |
|
173 | + */ |
|
174 | + public static $i18n_js_strings = array(); |
|
175 | + |
|
176 | + |
|
177 | + /** |
|
178 | + * $main_file - path to espresso.php |
|
179 | + * |
|
180 | + * @access public |
|
181 | + * @var array |
|
182 | + */ |
|
183 | + public $main_file; |
|
184 | + |
|
185 | + /** |
|
186 | + * array of ReflectionClass objects where the key is the class name |
|
187 | + * |
|
188 | + * @access public |
|
189 | + * @var ReflectionClass[] |
|
190 | + */ |
|
191 | + public $_reflectors; |
|
192 | + |
|
193 | + /** |
|
194 | + * boolean flag to indicate whether or not to load/save dependencies from/to the cache |
|
195 | + * |
|
196 | + * @access protected |
|
197 | + * @var boolean $_cache_on |
|
198 | + */ |
|
199 | + protected $_cache_on = true; |
|
200 | + |
|
201 | + |
|
202 | + |
|
203 | + /** |
|
204 | + * @singleton method used to instantiate class object |
|
205 | + * @access public |
|
206 | + * @param \EE_Dependency_Map $dependency_map |
|
207 | + * @return \EE_Registry instance |
|
208 | + */ |
|
209 | + public static function instance(\EE_Dependency_Map $dependency_map = null) |
|
210 | + { |
|
211 | + // check if class object is instantiated |
|
212 | + if ( ! self::$_instance instanceof EE_Registry) { |
|
213 | + self::$_instance = new EE_Registry($dependency_map); |
|
214 | + } |
|
215 | + return self::$_instance; |
|
216 | + } |
|
217 | + |
|
218 | + |
|
219 | + |
|
220 | + /** |
|
221 | + *protected constructor to prevent direct creation |
|
222 | + * |
|
223 | + * @Constructor |
|
224 | + * @access protected |
|
225 | + * @param \EE_Dependency_Map $dependency_map |
|
226 | + */ |
|
227 | + protected function __construct(\EE_Dependency_Map $dependency_map) |
|
228 | + { |
|
229 | + $this->_dependency_map = $dependency_map; |
|
230 | + $this->LIB = new stdClass(); |
|
231 | + $this->addons = new stdClass(); |
|
232 | + $this->modules = new stdClass(); |
|
233 | + $this->shortcodes = new stdClass(); |
|
234 | + $this->widgets = new stdClass(); |
|
235 | + add_action('EE_Load_Espresso_Core__handle_request__initialize_core_loading', array($this, 'initialize')); |
|
236 | + } |
|
237 | + |
|
238 | + |
|
239 | + |
|
240 | + /** |
|
241 | + * initialize |
|
242 | + */ |
|
243 | + public function initialize() |
|
244 | + { |
|
245 | + $this->_class_abbreviations = apply_filters( |
|
246 | + 'FHEE__EE_Registry____construct___class_abbreviations', |
|
247 | + array( |
|
248 | + 'EE_Config' => 'CFG', |
|
249 | + 'EE_Session' => 'SSN', |
|
250 | + 'EE_Capabilities' => 'CAP', |
|
251 | + 'EE_Cart' => 'CART', |
|
252 | + 'EE_Network_Config' => 'NET_CFG', |
|
253 | + 'EE_Request_Handler' => 'REQ', |
|
254 | + 'EE_Message_Resource_Manager' => 'MRM', |
|
255 | + 'EventEspresso\core\services\commands\CommandBus' => 'BUS', |
|
256 | + 'EventEspresso\core\services\assets\Registry' => 'AssetsRegistry', |
|
257 | + ) |
|
258 | + ); |
|
259 | + $this->load_core('Base', array(), true); |
|
260 | + // add our request and response objects to the cache |
|
261 | + $request_loader = $this->_dependency_map->class_loader('EE_Request'); |
|
262 | + $this->_set_cached_class( |
|
263 | + $request_loader(), |
|
264 | + 'EE_Request' |
|
265 | + ); |
|
266 | + $response_loader = $this->_dependency_map->class_loader('EE_Response'); |
|
267 | + $this->_set_cached_class( |
|
268 | + $response_loader(), |
|
269 | + 'EE_Response' |
|
270 | + ); |
|
271 | + add_action('AHEE__EE_System__set_hooks_for_core', array($this, 'init')); |
|
272 | + } |
|
273 | + |
|
274 | + |
|
275 | + |
|
276 | + /** |
|
277 | + * init |
|
278 | + * |
|
279 | + * @access public |
|
280 | + * @return void |
|
281 | + */ |
|
282 | + public function init() |
|
283 | + { |
|
284 | + // Get current page protocol |
|
285 | + $protocol = isset($_SERVER['HTTPS']) ? 'https://' : 'http://'; |
|
286 | + // Output admin-ajax.php URL with same protocol as current page |
|
287 | + self::$i18n_js_strings['ajax_url'] = admin_url('admin-ajax.php', $protocol); |
|
288 | + self::$i18n_js_strings['wp_debug'] = defined('WP_DEBUG') ? WP_DEBUG : false; |
|
289 | + } |
|
290 | + |
|
291 | + |
|
292 | + |
|
293 | + /** |
|
294 | + * localize_i18n_js_strings |
|
295 | + * |
|
296 | + * @return string |
|
297 | + */ |
|
298 | + public static function localize_i18n_js_strings() |
|
299 | + { |
|
300 | + $i18n_js_strings = (array)EE_Registry::$i18n_js_strings; |
|
301 | + foreach ($i18n_js_strings as $key => $value) { |
|
302 | + if (is_scalar($value)) { |
|
303 | + $i18n_js_strings[$key] = html_entity_decode((string)$value, ENT_QUOTES, 'UTF-8'); |
|
304 | + } |
|
305 | + } |
|
306 | + return "/* <![CDATA[ */ var eei18n = " . wp_json_encode($i18n_js_strings) . '; /* ]]> */'; |
|
307 | + } |
|
308 | + |
|
309 | + |
|
310 | + |
|
311 | + /** |
|
312 | + * @param mixed string | EED_Module $module |
|
313 | + */ |
|
314 | + public function add_module($module) |
|
315 | + { |
|
316 | + if ($module instanceof EED_Module) { |
|
317 | + $module_class = get_class($module); |
|
318 | + $this->modules->{$module_class} = $module; |
|
319 | + } else { |
|
320 | + if ( ! class_exists('EE_Module_Request_Router', false)) { |
|
321 | + $this->load_core('Module_Request_Router'); |
|
322 | + } |
|
323 | + $this->modules->{$module} = EE_Module_Request_Router::module_factory($module); |
|
324 | + } |
|
325 | + } |
|
326 | + |
|
327 | + |
|
328 | + |
|
329 | + /** |
|
330 | + * @param string $module_name |
|
331 | + * @return mixed EED_Module | NULL |
|
332 | + */ |
|
333 | + public function get_module($module_name = '') |
|
334 | + { |
|
335 | + return isset($this->modules->{$module_name}) ? $this->modules->{$module_name} : null; |
|
336 | + } |
|
337 | + |
|
338 | + |
|
339 | + |
|
340 | + /** |
|
341 | + * loads core classes - must be singletons |
|
342 | + * |
|
343 | + * @access public |
|
344 | + * @param string $class_name - simple class name ie: session |
|
345 | + * @param mixed $arguments |
|
346 | + * @param bool $load_only |
|
347 | + * @return mixed |
|
348 | + */ |
|
349 | + public function load_core($class_name, $arguments = array(), $load_only = false) |
|
350 | + { |
|
351 | + $core_paths = apply_filters( |
|
352 | + 'FHEE__EE_Registry__load_core__core_paths', |
|
353 | + array( |
|
354 | + EE_CORE, |
|
355 | + EE_ADMIN, |
|
356 | + EE_CPTS, |
|
357 | + EE_CORE . 'data_migration_scripts' . DS, |
|
358 | + EE_CORE . 'request_stack' . DS, |
|
359 | + EE_CORE . 'middleware' . DS, |
|
360 | + ) |
|
361 | + ); |
|
362 | + // retrieve instantiated class |
|
363 | + return $this->_load($core_paths, 'EE_', $class_name, 'core', $arguments, false, true, $load_only); |
|
364 | + } |
|
365 | + |
|
366 | + |
|
367 | + |
|
368 | + /** |
|
369 | + * loads service classes |
|
370 | + * |
|
371 | + * @access public |
|
372 | + * @param string $class_name - simple class name ie: session |
|
373 | + * @param mixed $arguments |
|
374 | + * @param bool $load_only |
|
375 | + * @return mixed |
|
376 | + */ |
|
377 | + public function load_service($class_name, $arguments = array(), $load_only = false) |
|
378 | + { |
|
379 | + $service_paths = apply_filters( |
|
380 | + 'FHEE__EE_Registry__load_service__service_paths', |
|
381 | + array( |
|
382 | + EE_CORE . 'services' . DS, |
|
383 | + ) |
|
384 | + ); |
|
385 | + // retrieve instantiated class |
|
386 | + return $this->_load($service_paths, 'EE_', $class_name, 'class', $arguments, false, true, $load_only); |
|
387 | + } |
|
388 | + |
|
389 | + |
|
390 | + |
|
391 | + /** |
|
392 | + * loads data_migration_scripts |
|
393 | + * |
|
394 | + * @access public |
|
395 | + * @param string $class_name - class name for the DMS ie: EE_DMS_Core_4_2_0 |
|
396 | + * @param mixed $arguments |
|
397 | + * @return EE_Data_Migration_Script_Base|mixed |
|
398 | + */ |
|
399 | + public function load_dms($class_name, $arguments = array()) |
|
400 | + { |
|
401 | + // retrieve instantiated class |
|
402 | + return $this->_load(EE_Data_Migration_Manager::instance()->get_data_migration_script_folders(), 'EE_DMS_', $class_name, 'dms', $arguments, false, false, false); |
|
403 | + } |
|
404 | + |
|
405 | + |
|
406 | + |
|
407 | + /** |
|
408 | + * loads object creating classes - must be singletons |
|
409 | + * |
|
410 | + * @param string $class_name - simple class name ie: attendee |
|
411 | + * @param mixed $arguments - an array of arguments to pass to the class |
|
412 | + * @param bool $from_db - some classes are instantiated from the db and thus call a different method to instantiate |
|
413 | + * @param bool $cache if you don't want the class to be stored in the internal cache (non-persistent) then set this to FALSE (ie. when instantiating model objects from client in a loop) |
|
414 | + * @param bool $load_only whether or not to just load the file and NOT instantiate, or load AND instantiate (default) |
|
415 | + * @return EE_Base_Class | bool |
|
416 | + */ |
|
417 | + public function load_class($class_name, $arguments = array(), $from_db = false, $cache = true, $load_only = false) |
|
418 | + { |
|
419 | + $paths = apply_filters('FHEE__EE_Registry__load_class__paths', array( |
|
420 | + EE_CORE, |
|
421 | + EE_CLASSES, |
|
422 | + EE_BUSINESS, |
|
423 | + )); |
|
424 | + // retrieve instantiated class |
|
425 | + return $this->_load($paths, 'EE_', $class_name, 'class', $arguments, $from_db, $cache, $load_only); |
|
426 | + } |
|
427 | + |
|
428 | + |
|
429 | + |
|
430 | + /** |
|
431 | + * loads helper classes - must be singletons |
|
432 | + * |
|
433 | + * @param string $class_name - simple class name ie: price |
|
434 | + * @param mixed $arguments |
|
435 | + * @param bool $load_only |
|
436 | + * @return EEH_Base | bool |
|
437 | + */ |
|
438 | + public function load_helper($class_name, $arguments = array(), $load_only = true) |
|
439 | + { |
|
440 | + // todo: add doing_it_wrong() in a few versions after all addons have had calls to this method removed |
|
441 | + $helper_paths = apply_filters('FHEE__EE_Registry__load_helper__helper_paths', array(EE_HELPERS)); |
|
442 | + // retrieve instantiated class |
|
443 | + return $this->_load($helper_paths, 'EEH_', $class_name, 'helper', $arguments, false, true, $load_only); |
|
444 | + } |
|
445 | + |
|
446 | + |
|
447 | + |
|
448 | + /** |
|
449 | + * loads core classes - must be singletons |
|
450 | + * |
|
451 | + * @access public |
|
452 | + * @param string $class_name - simple class name ie: session |
|
453 | + * @param mixed $arguments |
|
454 | + * @param bool $load_only |
|
455 | + * @param bool $cache whether to cache the object or not. |
|
456 | + * @return mixed |
|
457 | + */ |
|
458 | + public function load_lib($class_name, $arguments = array(), $load_only = false, $cache = true) |
|
459 | + { |
|
460 | + $paths = array( |
|
461 | + EE_LIBRARIES, |
|
462 | + EE_LIBRARIES . 'messages' . DS, |
|
463 | + EE_LIBRARIES . 'shortcodes' . DS, |
|
464 | + EE_LIBRARIES . 'qtips' . DS, |
|
465 | + EE_LIBRARIES . 'payment_methods' . DS, |
|
466 | + EE_LIBRARIES . 'messages' . DS . 'defaults' . DS, |
|
467 | + ); |
|
468 | + // retrieve instantiated class |
|
469 | + return $this->_load($paths, 'EE_', $class_name, 'lib', $arguments, false, $cache, $load_only); |
|
470 | + } |
|
471 | + |
|
472 | + |
|
473 | + |
|
474 | + /** |
|
475 | + * loads model classes - must be singletons |
|
476 | + * |
|
477 | + * @param string $class_name - simple class name ie: price |
|
478 | + * @param mixed $arguments |
|
479 | + * @param bool $load_only |
|
480 | + * @return EEM_Base | bool |
|
481 | + */ |
|
482 | + public function load_model($class_name, $arguments = array(), $load_only = false) |
|
483 | + { |
|
484 | + $paths = apply_filters('FHEE__EE_Registry__load_model__paths', array( |
|
485 | + EE_MODELS, |
|
486 | + EE_CORE, |
|
487 | + )); |
|
488 | + // retrieve instantiated class |
|
489 | + return $this->_load($paths, 'EEM_', $class_name, 'model', $arguments, false, true, $load_only); |
|
490 | + } |
|
491 | + |
|
492 | + |
|
493 | + |
|
494 | + /** |
|
495 | + * loads model classes - must be singletons |
|
496 | + * |
|
497 | + * @param string $class_name - simple class name ie: price |
|
498 | + * @param mixed $arguments |
|
499 | + * @param bool $load_only |
|
500 | + * @return mixed | bool |
|
501 | + */ |
|
502 | + public function load_model_class($class_name, $arguments = array(), $load_only = true) |
|
503 | + { |
|
504 | + $paths = array( |
|
505 | + EE_MODELS . 'fields' . DS, |
|
506 | + EE_MODELS . 'helpers' . DS, |
|
507 | + EE_MODELS . 'relations' . DS, |
|
508 | + EE_MODELS . 'strategies' . DS, |
|
509 | + ); |
|
510 | + // retrieve instantiated class |
|
511 | + return $this->_load($paths, 'EE_', $class_name, '', $arguments, false, true, $load_only); |
|
512 | + } |
|
513 | + |
|
514 | + |
|
515 | + |
|
516 | + /** |
|
517 | + * Determines if $model_name is the name of an actual EE model. |
|
518 | + * |
|
519 | + * @param string $model_name like Event, Attendee, Question_Group_Question, etc. |
|
520 | + * @return boolean |
|
521 | + */ |
|
522 | + public function is_model_name($model_name) |
|
523 | + { |
|
524 | + return isset($this->models[$model_name]) ? true : false; |
|
525 | + } |
|
526 | + |
|
527 | + |
|
528 | + |
|
529 | + /** |
|
530 | + * generic class loader |
|
531 | + * |
|
532 | + * @param string $path_to_file - directory path to file location, not including filename |
|
533 | + * @param string $file_name - file name ie: my_file.php, including extension |
|
534 | + * @param string $type - file type - core? class? helper? model? |
|
535 | + * @param mixed $arguments |
|
536 | + * @param bool $load_only |
|
537 | + * @return mixed |
|
538 | + */ |
|
539 | + public function load_file($path_to_file, $file_name, $type = '', $arguments = array(), $load_only = true) |
|
540 | + { |
|
541 | + // retrieve instantiated class |
|
542 | + return $this->_load($path_to_file, '', $file_name, $type, $arguments, false, true, $load_only); |
|
543 | + } |
|
544 | + |
|
545 | + |
|
546 | + |
|
547 | + /** |
|
548 | + * load_addon |
|
549 | + * |
|
550 | + * @param string $path_to_file - directory path to file location, not including filename |
|
551 | + * @param string $class_name - full class name ie: My_Class |
|
552 | + * @param string $type - file type - core? class? helper? model? |
|
553 | + * @param mixed $arguments |
|
554 | + * @param bool $load_only |
|
555 | + * @return EE_Addon |
|
556 | + */ |
|
557 | + public function load_addon($path_to_file, $class_name, $type = 'class', $arguments = array(), $load_only = false) |
|
558 | + { |
|
559 | + // retrieve instantiated class |
|
560 | + return $this->_load($path_to_file, 'addon', $class_name, $type, $arguments, false, true, $load_only); |
|
561 | + } |
|
562 | + |
|
563 | + |
|
564 | + |
|
565 | + /** |
|
566 | + * instantiates, caches, and automatically resolves dependencies |
|
567 | + * for classes that use a Fully Qualified Class Name. |
|
568 | + * if the class is not capable of being loaded using PSR-4 autoloading, |
|
569 | + * then you need to use one of the existing load_*() methods |
|
570 | + * which can resolve the classname and filepath from the passed arguments |
|
571 | + * |
|
572 | + * @param bool|string $class_name Fully Qualified Class Name |
|
573 | + * @param array $arguments an argument, or array of arguments to pass to the class upon instantiation |
|
574 | + * @param bool $cache whether to cache the instantiated object for reuse |
|
575 | + * @param bool $from_db some classes are instantiated from the db |
|
576 | + * and thus call a different method to instantiate |
|
577 | + * @param bool $load_only if true, will only load the file, but will NOT instantiate an object |
|
578 | + * @param bool|string $addon if true, will cache the object in the EE_Registry->$addons array |
|
579 | + * @return mixed null = failure to load or instantiate class object. |
|
580 | + * object = class loaded and instantiated successfully. |
|
581 | + * bool = fail or success when $load_only is true |
|
582 | + */ |
|
583 | + public function create( |
|
584 | + $class_name = false, |
|
585 | + $arguments = array(), |
|
586 | + $cache = false, |
|
587 | + $from_db = false, |
|
588 | + $load_only = false, |
|
589 | + $addon = false |
|
590 | + ) { |
|
591 | + $class_name = ltrim($class_name, '\\'); |
|
592 | + $class_name = $this->_dependency_map->get_alias($class_name); |
|
593 | + if ( ! class_exists($class_name)) { |
|
594 | + // maybe the class is registered with a preceding \ |
|
595 | + $class_name = strpos($class_name, '\\') !== 0 ? '\\' . $class_name : $class_name; |
|
596 | + // still doesn't exist ? |
|
597 | + if ( ! class_exists($class_name)) { |
|
598 | + return null; |
|
599 | + } |
|
600 | + } |
|
601 | + // if we're only loading the class and it already exists, then let's just return true immediately |
|
602 | + if ($load_only) { |
|
603 | + return true; |
|
604 | + } |
|
605 | + $addon = $addon ? 'addon' : ''; |
|
606 | + // $this->_cache_on is toggled during the recursive loading that can occur with dependency injection |
|
607 | + // $cache is controlled by individual calls to separate Registry loader methods like load_class() |
|
608 | + // $load_only is also controlled by individual calls to separate Registry loader methods like load_file() |
|
609 | + if ($this->_cache_on && $cache && ! $load_only) { |
|
610 | + // return object if it's already cached |
|
611 | + $cached_class = $this->_get_cached_class($class_name, $addon); |
|
612 | + if ($cached_class !== null) { |
|
613 | + return $cached_class; |
|
614 | + } |
|
615 | + } |
|
616 | + // instantiate the requested object |
|
617 | + $class_obj = $this->_create_object($class_name, $arguments, $addon, $from_db); |
|
618 | + if ($this->_cache_on && $cache) { |
|
619 | + // save it for later... kinda like gum { : $ |
|
620 | + $this->_set_cached_class($class_obj, $class_name, $addon, $from_db); |
|
621 | + } |
|
622 | + $this->_cache_on = true; |
|
623 | + return $class_obj; |
|
624 | + } |
|
625 | + |
|
626 | + |
|
627 | + |
|
628 | + /** |
|
629 | + * instantiates, caches, and injects dependencies for classes |
|
630 | + * |
|
631 | + * @param array $file_paths an array of paths to folders to look in |
|
632 | + * @param string $class_prefix EE or EEM or... ??? |
|
633 | + * @param bool|string $class_name $class name |
|
634 | + * @param string $type file type - core? class? helper? model? |
|
635 | + * @param mixed $arguments an argument or array of arguments to pass to the class upon instantiation |
|
636 | + * @param bool $from_db some classes are instantiated from the db |
|
637 | + * and thus call a different method to instantiate |
|
638 | + * @param bool $cache whether to cache the instantiated object for reuse |
|
639 | + * @param bool $load_only if true, will only load the file, but will NOT instantiate an object |
|
640 | + * @return null|object|bool null = failure to load or instantiate class object. |
|
641 | + * object = class loaded and instantiated successfully. |
|
642 | + * bool = fail or success when $load_only is true |
|
643 | + */ |
|
644 | + protected function _load( |
|
645 | + $file_paths = array(), |
|
646 | + $class_prefix = 'EE_', |
|
647 | + $class_name = false, |
|
648 | + $type = 'class', |
|
649 | + $arguments = array(), |
|
650 | + $from_db = false, |
|
651 | + $cache = true, |
|
652 | + $load_only = false |
|
653 | + ) { |
|
654 | + $class_name = ltrim($class_name, '\\'); |
|
655 | + // strip php file extension |
|
656 | + $class_name = str_replace('.php', '', trim($class_name)); |
|
657 | + // does the class have a prefix ? |
|
658 | + if ( ! empty($class_prefix) && $class_prefix != 'addon') { |
|
659 | + // make sure $class_prefix is uppercase |
|
660 | + $class_prefix = strtoupper(trim($class_prefix)); |
|
661 | + // add class prefix ONCE!!! |
|
662 | + $class_name = $class_prefix . str_replace($class_prefix, '', $class_name); |
|
663 | + } |
|
664 | + $class_name = $this->_dependency_map->get_alias($class_name); |
|
665 | + $class_exists = class_exists($class_name, false); |
|
666 | + // if we're only loading the class and it already exists, then let's just return true immediately |
|
667 | + if ($load_only && $class_exists) { |
|
668 | + return true; |
|
669 | + } |
|
670 | + // $this->_cache_on is toggled during the recursive loading that can occur with dependency injection |
|
671 | + // $cache is controlled by individual calls to separate Registry loader methods like load_class() |
|
672 | + // $load_only is also controlled by individual calls to separate Registry loader methods like load_file() |
|
673 | + if ($this->_cache_on && $cache && ! $load_only) { |
|
674 | + // return object if it's already cached |
|
675 | + $cached_class = $this->_get_cached_class($class_name, $class_prefix); |
|
676 | + if ($cached_class !== null) { |
|
677 | + return $cached_class; |
|
678 | + } |
|
679 | + } |
|
680 | + // if the class doesn't already exist.. then we need to try and find the file and load it |
|
681 | + if ( ! $class_exists) { |
|
682 | + // get full path to file |
|
683 | + $path = $this->_resolve_path($class_name, $type, $file_paths); |
|
684 | + // load the file |
|
685 | + $loaded = $this->_require_file($path, $class_name, $type, $file_paths); |
|
686 | + // if loading failed, or we are only loading a file but NOT instantiating an object |
|
687 | + if ( ! $loaded || $load_only) { |
|
688 | + // return boolean if only loading, or null if an object was expected |
|
689 | + return $load_only ? $loaded : null; |
|
690 | + } |
|
691 | + } |
|
692 | + // instantiate the requested object |
|
693 | + $class_obj = $this->_create_object($class_name, $arguments, $type, $from_db); |
|
694 | + if ($this->_cache_on && $cache) { |
|
695 | + // save it for later... kinda like gum { : $ |
|
696 | + $this->_set_cached_class($class_obj, $class_name, $class_prefix, $from_db); |
|
697 | + } |
|
698 | + $this->_cache_on = true; |
|
699 | + return $class_obj; |
|
700 | + } |
|
701 | + |
|
702 | + |
|
703 | + |
|
704 | + |
|
705 | + /** |
|
706 | + * _get_cached_class |
|
707 | + * attempts to find a cached version of the requested class |
|
708 | + * by looking in the following places: |
|
709 | + * $this->{$class_abbreviation} ie: $this->CART |
|
710 | + * $this->{$class_name} ie: $this->Some_Class |
|
711 | + * $this->LIB->{$class_name} ie: $this->LIB->Some_Class |
|
712 | + * $this->addon->{$class_name} ie: $this->addon->Some_Addon_Class |
|
713 | + * |
|
714 | + * @access protected |
|
715 | + * @param string $class_name |
|
716 | + * @param string $class_prefix |
|
717 | + * @return mixed |
|
718 | + */ |
|
719 | + protected function _get_cached_class($class_name, $class_prefix = '') |
|
720 | + { |
|
721 | + if ($class_name === 'EE_Registry') { |
|
722 | + return $this; |
|
723 | + } |
|
724 | + // have to specify something, but not anything that will conflict |
|
725 | + $class_abbreviation = isset($this->_class_abbreviations[ $class_name ]) |
|
726 | + ? $this->_class_abbreviations[ $class_name ] |
|
727 | + : 'FANCY_BATMAN_PANTS'; |
|
728 | + $class_name = str_replace('\\', '_', $class_name); |
|
729 | + // check if class has already been loaded, and return it if it has been |
|
730 | + if (isset($this->{$class_abbreviation}) && ! is_null($this->{$class_abbreviation})) { |
|
731 | + return $this->{$class_abbreviation}; |
|
732 | + } |
|
733 | + if (isset ($this->{$class_name})) { |
|
734 | + return $this->{$class_name}; |
|
735 | + } |
|
736 | + if (isset ($this->LIB->{$class_name})) { |
|
737 | + return $this->LIB->{$class_name}; |
|
738 | + } |
|
739 | + if ($class_prefix === 'addon' && isset ($this->addons->{$class_name})) { |
|
740 | + return $this->addons->{$class_name}; |
|
741 | + } |
|
742 | + return null; |
|
743 | + } |
|
744 | + |
|
745 | + |
|
746 | + |
|
747 | + /** |
|
748 | + * removes a cached version of the requested class |
|
749 | + * |
|
750 | + * @param string $class_name |
|
751 | + * @param boolean $addon |
|
752 | + * @return boolean |
|
753 | + */ |
|
754 | + public function clear_cached_class($class_name, $addon = false) |
|
755 | + { |
|
756 | + // have to specify something, but not anything that will conflict |
|
757 | + $class_abbreviation = isset($this->_class_abbreviations[ $class_name ]) |
|
758 | + ? $this->_class_abbreviations[ $class_name ] |
|
759 | + : 'FANCY_BATMAN_PANTS'; |
|
760 | + $class_name = str_replace('\\', '_', $class_name); |
|
761 | + // check if class has already been loaded, and return it if it has been |
|
762 | + if (isset($this->{$class_abbreviation}) && ! is_null($this->{$class_abbreviation})) { |
|
763 | + $this->{$class_abbreviation} = null; |
|
764 | + return true; |
|
765 | + } |
|
766 | + if (isset($this->{$class_name})) { |
|
767 | + $this->{$class_name} = null; |
|
768 | + return true; |
|
769 | + } |
|
770 | + if (isset($this->LIB->{$class_name})) { |
|
771 | + unset($this->LIB->{$class_name}); |
|
772 | + return true; |
|
773 | + } |
|
774 | + if ($addon && isset($this->addons->{$class_name})) { |
|
775 | + unset($this->addons->{$class_name}); |
|
776 | + return true; |
|
777 | + } |
|
778 | + return false; |
|
779 | + } |
|
780 | + |
|
781 | + |
|
782 | + /** |
|
783 | + * _resolve_path |
|
784 | + * attempts to find a full valid filepath for the requested class. |
|
785 | + * loops thru each of the base paths in the $file_paths array and appends : "{classname} . {file type} . php" |
|
786 | + * then returns that path if the target file has been found and is readable |
|
787 | + * |
|
788 | + * @access protected |
|
789 | + * @param string $class_name |
|
790 | + * @param string $type |
|
791 | + * @param array $file_paths |
|
792 | + * @return string | bool |
|
793 | + */ |
|
794 | + protected function _resolve_path($class_name, $type = '', $file_paths = array()) |
|
795 | + { |
|
796 | + // make sure $file_paths is an array |
|
797 | + $file_paths = is_array($file_paths) ? $file_paths : array($file_paths); |
|
798 | + // cycle thru paths |
|
799 | + foreach ($file_paths as $key => $file_path) { |
|
800 | + // convert all separators to proper DS, if no filepath, then use EE_CLASSES |
|
801 | + $file_path = $file_path ? str_replace(array('/', '\\'), DS, $file_path) : EE_CLASSES; |
|
802 | + // prep file type |
|
803 | + $type = ! empty($type) ? trim($type, '.') . '.' : ''; |
|
804 | + // build full file path |
|
805 | + $file_paths[$key] = rtrim($file_path, DS) . DS . $class_name . '.' . $type . 'php'; |
|
806 | + //does the file exist and can be read ? |
|
807 | + if (is_readable($file_paths[$key])) { |
|
808 | + return $file_paths[$key]; |
|
809 | + } |
|
810 | + } |
|
811 | + return false; |
|
812 | + } |
|
813 | + |
|
814 | + |
|
815 | + |
|
816 | + /** |
|
817 | + * _require_file |
|
818 | + * basically just performs a require_once() |
|
819 | + * but with some error handling |
|
820 | + * |
|
821 | + * @access protected |
|
822 | + * @param string $path |
|
823 | + * @param string $class_name |
|
824 | + * @param string $type |
|
825 | + * @param array $file_paths |
|
826 | + * @return boolean |
|
827 | + * @throws \EE_Error |
|
828 | + */ |
|
829 | + protected function _require_file($path, $class_name, $type = '', $file_paths = array()) |
|
830 | + { |
|
831 | + $this->resolve_legacy_class_parent($class_name); |
|
832 | + // don't give up! you gotta... |
|
833 | + try { |
|
834 | + //does the file exist and can it be read ? |
|
835 | + if ( ! $path) { |
|
836 | + // so sorry, can't find the file |
|
837 | + throw new EE_Error ( |
|
838 | + sprintf( |
|
839 | + __('The %1$s file %2$s could not be located or is not readable due to file permissions. Please ensure that the following filepath(s) are correct: %3$s', 'event_espresso'), |
|
840 | + trim($type, '.'), |
|
841 | + $class_name, |
|
842 | + '<br />' . implode(',<br />', $file_paths) |
|
843 | + ) |
|
844 | + ); |
|
845 | + } |
|
846 | + // get the file |
|
847 | + require_once($path); |
|
848 | + // if the class isn't already declared somewhere |
|
849 | + if (class_exists($class_name, false) === false) { |
|
850 | + // so sorry, not a class |
|
851 | + throw new EE_Error( |
|
852 | + sprintf( |
|
853 | + __('The %s file %s does not appear to contain the %s Class.', 'event_espresso'), |
|
854 | + $type, |
|
855 | + $path, |
|
856 | + $class_name |
|
857 | + ) |
|
858 | + ); |
|
859 | + } |
|
860 | + } catch (EE_Error $e) { |
|
861 | + $e->get_error(); |
|
862 | + return false; |
|
863 | + } |
|
864 | + return true; |
|
865 | + } |
|
866 | + |
|
867 | + |
|
868 | + |
|
869 | + /** |
|
870 | + * Some of our legacy classes that extended a parent class would simply use a require() statement |
|
871 | + * before their class declaration in order to ensure that the parent class was loaded. |
|
872 | + * This is not ideal, but it's nearly impossible to determine the parent class of a non-namespaced class, |
|
873 | + * without triggering a fatal error because the parent class has yet to be loaded and therefore doesn't exist. |
|
874 | + * |
|
875 | + * @param string $class_name |
|
876 | + */ |
|
877 | + protected function resolve_legacy_class_parent($class_name = '') |
|
878 | + { |
|
879 | + try { |
|
880 | + $legacy_parent_class_map = array( |
|
881 | + 'EE_Payment_Processor' => 'core/business/EE_Processor_Base.class.php' |
|
882 | + ); |
|
883 | + if(isset($legacy_parent_class_map[$class_name])) { |
|
884 | + require_once EE_PLUGIN_DIR_PATH . $legacy_parent_class_map[$class_name]; |
|
885 | + } |
|
886 | + } catch (Exception $exception) { |
|
887 | + } |
|
888 | + } |
|
889 | + |
|
890 | + |
|
891 | + |
|
892 | + /** |
|
893 | + * _create_object |
|
894 | + * Attempts to instantiate the requested class via any of the |
|
895 | + * commonly used instantiation methods employed throughout EE. |
|
896 | + * The priority for instantiation is as follows: |
|
897 | + * - abstract classes or any class flagged as "load only" (no instantiation occurs) |
|
898 | + * - model objects via their 'new_instance_from_db' method |
|
899 | + * - model objects via their 'new_instance' method |
|
900 | + * - "singleton" classes" via their 'instance' method |
|
901 | + * - standard instantiable classes via their __constructor |
|
902 | + * Prior to instantiation, if the classname exists in the dependency_map, |
|
903 | + * then the constructor for the requested class will be examined to determine |
|
904 | + * if any dependencies exist, and if they can be injected. |
|
905 | + * If so, then those classes will be added to the array of arguments passed to the constructor |
|
906 | + * |
|
907 | + * @access protected |
|
908 | + * @param string $class_name |
|
909 | + * @param array $arguments |
|
910 | + * @param string $type |
|
911 | + * @param bool $from_db |
|
912 | + * @return null | object |
|
913 | + * @throws \EE_Error |
|
914 | + */ |
|
915 | + protected function _create_object($class_name, $arguments = array(), $type = '', $from_db = false) |
|
916 | + { |
|
917 | + $class_obj = null; |
|
918 | + $instantiation_mode = '0) none'; |
|
919 | + // don't give up! you gotta... |
|
920 | + try { |
|
921 | + // create reflection |
|
922 | + $reflector = $this->get_ReflectionClass($class_name); |
|
923 | + // make sure arguments are an array |
|
924 | + $arguments = is_array($arguments) ? $arguments : array($arguments); |
|
925 | + // and if arguments array is numerically and sequentially indexed, then we want it to remain as is, |
|
926 | + // else wrap it in an additional array so that it doesn't get split into multiple parameters |
|
927 | + $arguments = $this->_array_is_numerically_and_sequentially_indexed($arguments) |
|
928 | + ? $arguments |
|
929 | + : array($arguments); |
|
930 | + // attempt to inject dependencies ? |
|
931 | + if ($this->_dependency_map->has($class_name)) { |
|
932 | + $arguments = $this->_resolve_dependencies($reflector, $class_name, $arguments); |
|
933 | + } |
|
934 | + // instantiate the class if possible |
|
935 | + if ($reflector->isAbstract()) { |
|
936 | + // nothing to instantiate, loading file was enough |
|
937 | + // does not throw an exception so $instantiation_mode is unused |
|
938 | + // $instantiation_mode = "1) no constructor abstract class"; |
|
939 | + $class_obj = true; |
|
940 | + } else if ($reflector->getConstructor() === null && $reflector->isInstantiable() && empty($arguments)) { |
|
941 | + // no constructor = static methods only... nothing to instantiate, loading file was enough |
|
942 | + $instantiation_mode = "2) no constructor but instantiable"; |
|
943 | + $class_obj = $reflector->newInstance(); |
|
944 | + } else if ($from_db && method_exists($class_name, 'new_instance_from_db')) { |
|
945 | + $instantiation_mode = "3) new_instance_from_db()"; |
|
946 | + $class_obj = call_user_func_array(array($class_name, 'new_instance_from_db'), $arguments); |
|
947 | + } else if (method_exists($class_name, 'new_instance')) { |
|
948 | + $instantiation_mode = "4) new_instance()"; |
|
949 | + $class_obj = call_user_func_array(array($class_name, 'new_instance'), $arguments); |
|
950 | + } else if (method_exists($class_name, 'instance')) { |
|
951 | + $instantiation_mode = "5) instance()"; |
|
952 | + $class_obj = call_user_func_array(array($class_name, 'instance'), $arguments); |
|
953 | + } else if ($reflector->isInstantiable()) { |
|
954 | + $instantiation_mode = "6) constructor"; |
|
955 | + $class_obj = $reflector->newInstanceArgs($arguments); |
|
956 | + } else { |
|
957 | + // heh ? something's not right ! |
|
958 | + throw new EE_Error( |
|
959 | + sprintf( |
|
960 | + __('The %s file %s could not be instantiated.', 'event_espresso'), |
|
961 | + $type, |
|
962 | + $class_name |
|
963 | + ) |
|
964 | + ); |
|
965 | + } |
|
966 | + } catch (Exception $e) { |
|
967 | + if ( ! $e instanceof EE_Error) { |
|
968 | + $e = new EE_Error( |
|
969 | + sprintf( |
|
970 | + __('The following error occurred while attempting to instantiate "%1$s": %2$s %3$s %2$s instantiation mode : %4$s', 'event_espresso'), |
|
971 | + $class_name, |
|
972 | + '<br />', |
|
973 | + $e->getMessage(), |
|
974 | + $instantiation_mode |
|
975 | + ) |
|
976 | + ); |
|
977 | + } |
|
978 | + $e->get_error(); |
|
979 | + } |
|
980 | + return $class_obj; |
|
981 | + } |
|
982 | + |
|
983 | + |
|
984 | + |
|
985 | + /** |
|
986 | + * @see http://stackoverflow.com/questions/173400/how-to-check-if-php-array-is-associative-or-sequential |
|
987 | + * @param array $array |
|
988 | + * @return bool |
|
989 | + */ |
|
990 | + protected function _array_is_numerically_and_sequentially_indexed(array $array) |
|
991 | + { |
|
992 | + return ! empty($array) ? array_keys($array) === range(0, count($array) - 1) : true; |
|
993 | + } |
|
994 | + |
|
995 | + |
|
996 | + |
|
997 | + /** |
|
998 | + * getReflectionClass |
|
999 | + * checks if a ReflectionClass object has already been generated for a class |
|
1000 | + * and returns that instead of creating a new one |
|
1001 | + * |
|
1002 | + * @access public |
|
1003 | + * @param string $class_name |
|
1004 | + * @return ReflectionClass |
|
1005 | + */ |
|
1006 | + public function get_ReflectionClass($class_name) |
|
1007 | + { |
|
1008 | + if ( |
|
1009 | + ! isset($this->_reflectors[$class_name]) |
|
1010 | + || ! $this->_reflectors[$class_name] instanceof ReflectionClass |
|
1011 | + ) { |
|
1012 | + $this->_reflectors[$class_name] = new ReflectionClass($class_name); |
|
1013 | + } |
|
1014 | + return $this->_reflectors[$class_name]; |
|
1015 | + } |
|
1016 | + |
|
1017 | + |
|
1018 | + |
|
1019 | + /** |
|
1020 | + * _resolve_dependencies |
|
1021 | + * examines the constructor for the requested class to determine |
|
1022 | + * if any dependencies exist, and if they can be injected. |
|
1023 | + * If so, then those classes will be added to the array of arguments passed to the constructor |
|
1024 | + * PLZ NOTE: this is achieved by type hinting the constructor params |
|
1025 | + * For example: |
|
1026 | + * if attempting to load a class "Foo" with the following constructor: |
|
1027 | + * __construct( Bar $bar_class, Fighter $grohl_class ) |
|
1028 | + * then $bar_class and $grohl_class will be added to the $arguments array, |
|
1029 | + * but only IF they are NOT already present in the incoming arguments array, |
|
1030 | + * and the correct classes can be loaded |
|
1031 | + * |
|
1032 | + * @access protected |
|
1033 | + * @param ReflectionClass $reflector |
|
1034 | + * @param string $class_name |
|
1035 | + * @param array $arguments |
|
1036 | + * @return array |
|
1037 | + * @throws \ReflectionException |
|
1038 | + */ |
|
1039 | + protected function _resolve_dependencies(ReflectionClass $reflector, $class_name, $arguments = array()) |
|
1040 | + { |
|
1041 | + // let's examine the constructor |
|
1042 | + $constructor = $reflector->getConstructor(); |
|
1043 | + // whu? huh? nothing? |
|
1044 | + if ( ! $constructor) { |
|
1045 | + return $arguments; |
|
1046 | + } |
|
1047 | + // get constructor parameters |
|
1048 | + $params = $constructor->getParameters(); |
|
1049 | + // and the keys for the incoming arguments array so that we can compare existing arguments with what is expected |
|
1050 | + $argument_keys = array_keys($arguments); |
|
1051 | + // now loop thru all of the constructors expected parameters |
|
1052 | + foreach ($params as $index => $param) { |
|
1053 | + // is this a dependency for a specific class ? |
|
1054 | + $param_class = $param->getClass() ? $param->getClass()->name : null; |
|
1055 | + // BUT WAIT !!! This class may be an alias for something else (or getting replaced at runtime) |
|
1056 | + $param_class = $this->_dependency_map->has_alias($param_class, $class_name) |
|
1057 | + ? $this->_dependency_map->get_alias($param_class, $class_name) |
|
1058 | + : $param_class; |
|
1059 | + if ( |
|
1060 | + // param is not even a class |
|
1061 | + empty($param_class) |
|
1062 | + // and something already exists in the incoming arguments for this param |
|
1063 | + && isset($argument_keys[$index], $arguments[$argument_keys[$index]]) |
|
1064 | + ) { |
|
1065 | + // so let's skip this argument and move on to the next |
|
1066 | + continue; |
|
1067 | + } |
|
1068 | + if ( |
|
1069 | + // parameter is type hinted as a class, exists as an incoming argument, AND it's the correct class |
|
1070 | + ! empty($param_class) |
|
1071 | + && isset($argument_keys[$index], $arguments[$argument_keys[$index]]) |
|
1072 | + && $arguments[$argument_keys[$index]] instanceof $param_class |
|
1073 | + ) { |
|
1074 | + // skip this argument and move on to the next |
|
1075 | + continue; |
|
1076 | + } |
|
1077 | + if ( |
|
1078 | + // parameter is type hinted as a class, and should be injected |
|
1079 | + ! empty($param_class) |
|
1080 | + && $this->_dependency_map->has_dependency_for_class($class_name, $param_class) |
|
1081 | + ) { |
|
1082 | + $arguments = $this->_resolve_dependency($class_name, $param_class, $arguments, $index); |
|
1083 | + } else { |
|
1084 | + try { |
|
1085 | + $arguments[$index] = $param->getDefaultValue(); |
|
1086 | + } catch (ReflectionException $e) { |
|
1087 | + throw new ReflectionException( |
|
1088 | + sprintf( |
|
1089 | + __('%1$s for parameter "$%2$s"', 'event_espresso'), |
|
1090 | + $e->getMessage(), |
|
1091 | + $param->getName() |
|
1092 | + ) |
|
1093 | + ); |
|
1094 | + } |
|
1095 | + } |
|
1096 | + } |
|
1097 | + return $arguments; |
|
1098 | + } |
|
1099 | + |
|
1100 | + |
|
1101 | + |
|
1102 | + /** |
|
1103 | + * @access protected |
|
1104 | + * @param string $class_name |
|
1105 | + * @param string $param_class |
|
1106 | + * @param array $arguments |
|
1107 | + * @param mixed $index |
|
1108 | + * @return array |
|
1109 | + */ |
|
1110 | + protected function _resolve_dependency($class_name, $param_class, $arguments, $index) |
|
1111 | + { |
|
1112 | + $dependency = null; |
|
1113 | + // should dependency be loaded from cache ? |
|
1114 | + $cache_on = $this->_dependency_map->loading_strategy_for_class_dependency($class_name, $param_class) |
|
1115 | + !== EE_Dependency_Map::load_new_object |
|
1116 | + ? true |
|
1117 | + : false; |
|
1118 | + // we might have a dependency... |
|
1119 | + // let's MAYBE try and find it in our cache if that's what's been requested |
|
1120 | + $cached_class = $cache_on ? $this->_get_cached_class($param_class) : null; |
|
1121 | + // and grab it if it exists |
|
1122 | + if ($cached_class instanceof $param_class) { |
|
1123 | + $dependency = $cached_class; |
|
1124 | + } else if ($param_class !== $class_name) { |
|
1125 | + // obtain the loader method from the dependency map |
|
1126 | + $loader = $this->_dependency_map->class_loader($param_class); |
|
1127 | + // is loader a custom closure ? |
|
1128 | + if ($loader instanceof Closure) { |
|
1129 | + $dependency = $loader(); |
|
1130 | + } else { |
|
1131 | + // set the cache on property for the recursive loading call |
|
1132 | + $this->_cache_on = $cache_on; |
|
1133 | + // if not, then let's try and load it via the registry |
|
1134 | + if ($loader && method_exists($this, $loader)) { |
|
1135 | + $dependency = $this->{$loader}($param_class); |
|
1136 | + } else { |
|
1137 | + $dependency = $this->create($param_class, array(), $cache_on); |
|
1138 | + } |
|
1139 | + } |
|
1140 | + } |
|
1141 | + // did we successfully find the correct dependency ? |
|
1142 | + if ($dependency instanceof $param_class) { |
|
1143 | + // then let's inject it into the incoming array of arguments at the correct location |
|
1144 | + if (isset($argument_keys[$index])) { |
|
1145 | + $arguments[$argument_keys[$index]] = $dependency; |
|
1146 | + } else { |
|
1147 | + $arguments[$index] = $dependency; |
|
1148 | + } |
|
1149 | + } |
|
1150 | + return $arguments; |
|
1151 | + } |
|
1152 | + |
|
1153 | + |
|
1154 | + |
|
1155 | + /** |
|
1156 | + * _set_cached_class |
|
1157 | + * attempts to cache the instantiated class locally |
|
1158 | + * in one of the following places, in the following order: |
|
1159 | + * $this->{class_abbreviation} ie: $this->CART |
|
1160 | + * $this->{$class_name} ie: $this->Some_Class |
|
1161 | + * $this->addon->{$$class_name} ie: $this->addon->Some_Addon_Class |
|
1162 | + * $this->LIB->{$class_name} ie: $this->LIB->Some_Class |
|
1163 | + * |
|
1164 | + * @access protected |
|
1165 | + * @param object $class_obj |
|
1166 | + * @param string $class_name |
|
1167 | + * @param string $class_prefix |
|
1168 | + * @param bool $from_db |
|
1169 | + * @return void |
|
1170 | + */ |
|
1171 | + protected function _set_cached_class($class_obj, $class_name, $class_prefix = '', $from_db = false) |
|
1172 | + { |
|
1173 | + if ($class_name === 'EE_Registry' || empty($class_obj)) { |
|
1174 | + return; |
|
1175 | + } |
|
1176 | + // return newly instantiated class |
|
1177 | + if (isset($this->_class_abbreviations[$class_name])) { |
|
1178 | + $class_abbreviation = $this->_class_abbreviations[$class_name]; |
|
1179 | + $this->{$class_abbreviation} = $class_obj; |
|
1180 | + return; |
|
1181 | + } |
|
1182 | + $class_name = str_replace('\\', '_', $class_name); |
|
1183 | + if (property_exists($this, $class_name)) { |
|
1184 | + $this->{$class_name} = $class_obj; |
|
1185 | + return; |
|
1186 | + } |
|
1187 | + if ($class_prefix === 'addon') { |
|
1188 | + $this->addons->{$class_name} = $class_obj; |
|
1189 | + return; |
|
1190 | + } |
|
1191 | + if ( ! $from_db) { |
|
1192 | + $this->LIB->{$class_name} = $class_obj; |
|
1193 | + } |
|
1194 | + } |
|
1195 | + |
|
1196 | + |
|
1197 | + |
|
1198 | + /** |
|
1199 | + * call any loader that's been registered in the EE_Dependency_Map::$_class_loaders array |
|
1200 | + * |
|
1201 | + * @param string $classname PLEASE NOTE: the class name needs to match what's registered |
|
1202 | + * in the EE_Dependency_Map::$_class_loaders array, |
|
1203 | + * including the class prefix, ie: "EE_", "EEM_", "EEH_", etc |
|
1204 | + * @param array $arguments |
|
1205 | + * @return object |
|
1206 | + */ |
|
1207 | + public static function factory($classname, $arguments = array()) |
|
1208 | + { |
|
1209 | + $loader = self::instance()->_dependency_map->class_loader($classname); |
|
1210 | + if ($loader instanceof Closure) { |
|
1211 | + return $loader($arguments); |
|
1212 | + } |
|
1213 | + if (method_exists(EE_Registry::instance(), $loader)) { |
|
1214 | + return EE_Registry::instance()->{$loader}($classname, $arguments); |
|
1215 | + } |
|
1216 | + return null; |
|
1217 | + } |
|
1218 | + |
|
1219 | + |
|
1220 | + |
|
1221 | + /** |
|
1222 | + * Gets the addon by its name/slug (not classname. For that, just |
|
1223 | + * use the classname as the property name on EE_Config::instance()->addons) |
|
1224 | + * |
|
1225 | + * @param string $name |
|
1226 | + * @return EE_Addon |
|
1227 | + */ |
|
1228 | + public function get_addon_by_name($name) |
|
1229 | + { |
|
1230 | + foreach ($this->addons as $addon) { |
|
1231 | + if ($addon->name() == $name) { |
|
1232 | + return $addon; |
|
1233 | + } |
|
1234 | + } |
|
1235 | + return null; |
|
1236 | + } |
|
1237 | + |
|
1238 | + |
|
1239 | + |
|
1240 | + /** |
|
1241 | + * Gets an array of all the registered addons, where the keys are their names. (ie, what each returns for their name() function) They're already available on EE_Config::instance()->addons as properties, where each property's name is |
|
1242 | + * the addon's classname. So if you just want to get the addon by classname, use EE_Config::instance()->addons->{classname} |
|
1243 | + * |
|
1244 | + * @return EE_Addon[] where the KEYS are the addon's name() |
|
1245 | + */ |
|
1246 | + public function get_addons_by_name() |
|
1247 | + { |
|
1248 | + $addons = array(); |
|
1249 | + foreach ($this->addons as $addon) { |
|
1250 | + $addons[$addon->name()] = $addon; |
|
1251 | + } |
|
1252 | + return $addons; |
|
1253 | + } |
|
1254 | + |
|
1255 | + |
|
1256 | + |
|
1257 | + /** |
|
1258 | + * Resets the specified model's instance AND makes sure EE_Registry doesn't keep |
|
1259 | + * a stale copy of it around |
|
1260 | + * |
|
1261 | + * @param string $model_name |
|
1262 | + * @return \EEM_Base |
|
1263 | + * @throws \EE_Error |
|
1264 | + */ |
|
1265 | + public function reset_model($model_name) |
|
1266 | + { |
|
1267 | + $model_class_name = strpos($model_name, 'EEM_') !== 0 ? "EEM_{$model_name}" : $model_name; |
|
1268 | + if ( ! isset($this->LIB->{$model_class_name}) || ! $this->LIB->{$model_class_name} instanceof EEM_Base) { |
|
1269 | + return null; |
|
1270 | + } |
|
1271 | + //get that model reset it and make sure we nuke the old reference to it |
|
1272 | + if ($this->LIB->{$model_class_name} instanceof $model_class_name && is_callable(array($model_class_name, 'reset'))) { |
|
1273 | + $this->LIB->{$model_class_name} = $this->LIB->{$model_class_name}->reset(); |
|
1274 | + } else { |
|
1275 | + throw new EE_Error(sprintf(__('Model %s does not have a method "reset"', 'event_espresso'), $model_name)); |
|
1276 | + } |
|
1277 | + return $this->LIB->{$model_class_name}; |
|
1278 | + } |
|
1279 | + |
|
1280 | + |
|
1281 | + |
|
1282 | + /** |
|
1283 | + * Resets the registry. |
|
1284 | + * The criteria for what gets reset is based on what can be shared between sites on the same request when switch_to_blog |
|
1285 | + * is used in a multisite install. Here is a list of things that are NOT reset. |
|
1286 | + * - $_dependency_map |
|
1287 | + * - $_class_abbreviations |
|
1288 | + * - $NET_CFG (EE_Network_Config): The config is shared network wide so no need to reset. |
|
1289 | + * - $REQ: Still on the same request so no need to change. |
|
1290 | + * - $CAP: There is no site specific state in the EE_Capability class. |
|
1291 | + * - $SSN: Although ideally, the session should not be shared between site switches, we can't reset it because only one Session |
|
1292 | + * can be active in a single request. Resetting could resolve in "headers already sent" errors. |
|
1293 | + * - $addons: In multisite, the state of the addons is something controlled via hooks etc in a normal request. So |
|
1294 | + * for now, we won't reset the addons because it could break calls to an add-ons class/methods in the |
|
1295 | + * switch or on the restore. |
|
1296 | + * - $modules |
|
1297 | + * - $shortcodes |
|
1298 | + * - $widgets |
|
1299 | + * |
|
1300 | + * @param boolean $hard whether to reset data in the database too, or just refresh |
|
1301 | + * the Registry to its state at the beginning of the request |
|
1302 | + * @param boolean $reinstantiate whether to create new instances of EE_Registry's singletons too, |
|
1303 | + * or just reset without re-instantiating (handy to set to FALSE if you're not sure if you CAN |
|
1304 | + * currently reinstantiate the singletons at the moment) |
|
1305 | + * @param bool $reset_models Defaults to true. When false, then the models are not reset. This is so client |
|
1306 | + * code instead can just change the model context to a different blog id if necessary |
|
1307 | + * @return EE_Registry |
|
1308 | + */ |
|
1309 | + public static function reset($hard = false, $reinstantiate = true, $reset_models = true) |
|
1310 | + { |
|
1311 | + $instance = self::instance(); |
|
1312 | + $instance->_cache_on = true; |
|
1313 | + // reset some "special" classes |
|
1314 | + EEH_Activation::reset(); |
|
1315 | + $instance->CFG = $instance->CFG->reset($hard, $reinstantiate); |
|
1316 | + $instance->CART = null; |
|
1317 | + $instance->MRM = null; |
|
1318 | + $instance->AssetsRegistry = null; |
|
1319 | + $instance->AssetsRegistry = $instance->create('EventEspresso\core\services\assets\Registry'); |
|
1320 | + //messages reset |
|
1321 | + EED_Messages::reset(); |
|
1322 | + //handle of objects cached on LIB |
|
1323 | + foreach (array('LIB', 'modules', 'shortcodes') as $cache) { |
|
1324 | + foreach ($instance->{$cache} as $class_name => $class) { |
|
1325 | + if (EE_Registry::_reset_and_unset_object($class, $reset_models)) { |
|
1326 | + unset($instance->{$cache}->{$class_name}); |
|
1327 | + } |
|
1328 | + } |
|
1329 | + } |
|
1330 | + return $instance; |
|
1331 | + } |
|
1332 | + |
|
1333 | + |
|
1334 | + |
|
1335 | + /** |
|
1336 | + * if passed object implements ResettableInterface, then call it's reset() method |
|
1337 | + * if passed object implements InterminableInterface, then return false, |
|
1338 | + * to indicate that it should NOT be cleared from the Registry cache |
|
1339 | + * |
|
1340 | + * @param $object |
|
1341 | + * @param bool $reset_models |
|
1342 | + * @return bool returns true if cached object should be unset |
|
1343 | + */ |
|
1344 | + private static function _reset_and_unset_object($object, $reset_models) |
|
1345 | + { |
|
1346 | + static $count = 0; |
|
1347 | + $count++; |
|
1348 | + if ($object instanceof ResettableInterface) { |
|
1349 | + if ($object instanceof EEM_Base) { |
|
1350 | + if ($reset_models) { |
|
1351 | + $object->reset(); |
|
1352 | + return true; |
|
1353 | + } |
|
1354 | + return false; |
|
1355 | + } |
|
1356 | + $object->reset(); |
|
1357 | + return true; |
|
1358 | + } |
|
1359 | + if ( ! $object instanceof InterminableInterface) { |
|
1360 | + return true; |
|
1361 | + } |
|
1362 | + return false; |
|
1363 | + } |
|
1364 | + |
|
1365 | + |
|
1366 | + |
|
1367 | + /** |
|
1368 | + * @override magic methods |
|
1369 | + * @return void |
|
1370 | + */ |
|
1371 | + public final function __destruct() |
|
1372 | + { |
|
1373 | + } |
|
1374 | + |
|
1375 | + |
|
1376 | + |
|
1377 | + /** |
|
1378 | + * @param $a |
|
1379 | + * @param $b |
|
1380 | + */ |
|
1381 | + public final function __call($a, $b) |
|
1382 | + { |
|
1383 | + } |
|
1384 | + |
|
1385 | + |
|
1386 | + |
|
1387 | + /** |
|
1388 | + * @param $a |
|
1389 | + */ |
|
1390 | + public final function __get($a) |
|
1391 | + { |
|
1392 | + } |
|
1393 | + |
|
1394 | + |
|
1395 | + |
|
1396 | + /** |
|
1397 | + * @param $a |
|
1398 | + * @param $b |
|
1399 | + */ |
|
1400 | + public final function __set($a, $b) |
|
1401 | + { |
|
1402 | + } |
|
1403 | + |
|
1404 | + |
|
1405 | + |
|
1406 | + /** |
|
1407 | + * @param $a |
|
1408 | + */ |
|
1409 | + public final function __isset($a) |
|
1410 | + { |
|
1411 | + } |
|
1412 | 1412 | |
1413 | 1413 | |
1414 | 1414 | |
1415 | - /** |
|
1416 | - * @param $a |
|
1417 | - */ |
|
1418 | - public final function __unset($a) |
|
1419 | - { |
|
1420 | - } |
|
1415 | + /** |
|
1416 | + * @param $a |
|
1417 | + */ |
|
1418 | + public final function __unset($a) |
|
1419 | + { |
|
1420 | + } |
|
1421 | 1421 | |
1422 | 1422 | |
1423 | 1423 | |
1424 | - /** |
|
1425 | - * @return array |
|
1426 | - */ |
|
1427 | - public final function __sleep() |
|
1428 | - { |
|
1429 | - return array(); |
|
1430 | - } |
|
1424 | + /** |
|
1425 | + * @return array |
|
1426 | + */ |
|
1427 | + public final function __sleep() |
|
1428 | + { |
|
1429 | + return array(); |
|
1430 | + } |
|
1431 | 1431 | |
1432 | 1432 | |
1433 | 1433 | |
1434 | - public final function __wakeup() |
|
1435 | - { |
|
1436 | - } |
|
1434 | + public final function __wakeup() |
|
1435 | + { |
|
1436 | + } |
|
1437 | 1437 | |
1438 | 1438 | |
1439 | 1439 | |
1440 | - /** |
|
1441 | - * @return string |
|
1442 | - */ |
|
1443 | - public final function __toString() |
|
1444 | - { |
|
1445 | - return ''; |
|
1446 | - } |
|
1440 | + /** |
|
1441 | + * @return string |
|
1442 | + */ |
|
1443 | + public final function __toString() |
|
1444 | + { |
|
1445 | + return ''; |
|
1446 | + } |
|
1447 | 1447 | |
1448 | 1448 | |
1449 | 1449 | |
1450 | - public final function __invoke() |
|
1451 | - { |
|
1452 | - } |
|
1450 | + public final function __invoke() |
|
1451 | + { |
|
1452 | + } |
|
1453 | 1453 | |
1454 | 1454 | |
1455 | 1455 | |
1456 | - public final static function __set_state($array = array()) |
|
1457 | - { |
|
1458 | - return EE_Registry::instance(); |
|
1459 | - } |
|
1456 | + public final static function __set_state($array = array()) |
|
1457 | + { |
|
1458 | + return EE_Registry::instance(); |
|
1459 | + } |
|
1460 | 1460 | |
1461 | 1461 | |
1462 | 1462 | |
1463 | - public final function __clone() |
|
1464 | - { |
|
1465 | - } |
|
1463 | + public final function __clone() |
|
1464 | + { |
|
1465 | + } |
|
1466 | 1466 | |
1467 | 1467 | |
1468 | 1468 | |
1469 | - /** |
|
1470 | - * @param $a |
|
1471 | - * @param $b |
|
1472 | - */ |
|
1473 | - public final static function __callStatic($a, $b) |
|
1474 | - { |
|
1475 | - } |
|
1469 | + /** |
|
1470 | + * @param $a |
|
1471 | + * @param $b |
|
1472 | + */ |
|
1473 | + public final static function __callStatic($a, $b) |
|
1474 | + { |
|
1475 | + } |
|
1476 | 1476 | |
1477 | 1477 | |
1478 | 1478 | |
1479 | - /** |
|
1480 | - * Gets all the custom post type models defined |
|
1481 | - * |
|
1482 | - * @return array keys are model "short names" (Eg "Event") and keys are classnames (eg "EEM_Event") |
|
1483 | - */ |
|
1484 | - public function cpt_models() |
|
1485 | - { |
|
1486 | - $cpt_models = array(); |
|
1487 | - foreach ($this->non_abstract_db_models as $short_name => $classname) { |
|
1488 | - if (is_subclass_of($classname, 'EEM_CPT_Base')) { |
|
1489 | - $cpt_models[$short_name] = $classname; |
|
1490 | - } |
|
1491 | - } |
|
1492 | - return $cpt_models; |
|
1493 | - } |
|
1479 | + /** |
|
1480 | + * Gets all the custom post type models defined |
|
1481 | + * |
|
1482 | + * @return array keys are model "short names" (Eg "Event") and keys are classnames (eg "EEM_Event") |
|
1483 | + */ |
|
1484 | + public function cpt_models() |
|
1485 | + { |
|
1486 | + $cpt_models = array(); |
|
1487 | + foreach ($this->non_abstract_db_models as $short_name => $classname) { |
|
1488 | + if (is_subclass_of($classname, 'EEM_CPT_Base')) { |
|
1489 | + $cpt_models[$short_name] = $classname; |
|
1490 | + } |
|
1491 | + } |
|
1492 | + return $cpt_models; |
|
1493 | + } |
|
1494 | 1494 | |
1495 | 1495 | |
1496 | 1496 | |
1497 | - /** |
|
1498 | - * @return \EE_Config |
|
1499 | - */ |
|
1500 | - public static function CFG() |
|
1501 | - { |
|
1502 | - return self::instance()->CFG; |
|
1503 | - } |
|
1497 | + /** |
|
1498 | + * @return \EE_Config |
|
1499 | + */ |
|
1500 | + public static function CFG() |
|
1501 | + { |
|
1502 | + return self::instance()->CFG; |
|
1503 | + } |
|
1504 | 1504 | |
1505 | 1505 | |
1506 | 1506 | } |
@@ -297,13 +297,13 @@ discard block |
||
297 | 297 | */ |
298 | 298 | public static function localize_i18n_js_strings() |
299 | 299 | { |
300 | - $i18n_js_strings = (array)EE_Registry::$i18n_js_strings; |
|
300 | + $i18n_js_strings = (array) EE_Registry::$i18n_js_strings; |
|
301 | 301 | foreach ($i18n_js_strings as $key => $value) { |
302 | 302 | if (is_scalar($value)) { |
303 | - $i18n_js_strings[$key] = html_entity_decode((string)$value, ENT_QUOTES, 'UTF-8'); |
|
303 | + $i18n_js_strings[$key] = html_entity_decode((string) $value, ENT_QUOTES, 'UTF-8'); |
|
304 | 304 | } |
305 | 305 | } |
306 | - return "/* <![CDATA[ */ var eei18n = " . wp_json_encode($i18n_js_strings) . '; /* ]]> */'; |
|
306 | + return "/* <![CDATA[ */ var eei18n = ".wp_json_encode($i18n_js_strings).'; /* ]]> */'; |
|
307 | 307 | } |
308 | 308 | |
309 | 309 | |
@@ -354,9 +354,9 @@ discard block |
||
354 | 354 | EE_CORE, |
355 | 355 | EE_ADMIN, |
356 | 356 | EE_CPTS, |
357 | - EE_CORE . 'data_migration_scripts' . DS, |
|
358 | - EE_CORE . 'request_stack' . DS, |
|
359 | - EE_CORE . 'middleware' . DS, |
|
357 | + EE_CORE.'data_migration_scripts'.DS, |
|
358 | + EE_CORE.'request_stack'.DS, |
|
359 | + EE_CORE.'middleware'.DS, |
|
360 | 360 | ) |
361 | 361 | ); |
362 | 362 | // retrieve instantiated class |
@@ -379,7 +379,7 @@ discard block |
||
379 | 379 | $service_paths = apply_filters( |
380 | 380 | 'FHEE__EE_Registry__load_service__service_paths', |
381 | 381 | array( |
382 | - EE_CORE . 'services' . DS, |
|
382 | + EE_CORE.'services'.DS, |
|
383 | 383 | ) |
384 | 384 | ); |
385 | 385 | // retrieve instantiated class |
@@ -459,11 +459,11 @@ discard block |
||
459 | 459 | { |
460 | 460 | $paths = array( |
461 | 461 | EE_LIBRARIES, |
462 | - EE_LIBRARIES . 'messages' . DS, |
|
463 | - EE_LIBRARIES . 'shortcodes' . DS, |
|
464 | - EE_LIBRARIES . 'qtips' . DS, |
|
465 | - EE_LIBRARIES . 'payment_methods' . DS, |
|
466 | - EE_LIBRARIES . 'messages' . DS . 'defaults' . DS, |
|
462 | + EE_LIBRARIES.'messages'.DS, |
|
463 | + EE_LIBRARIES.'shortcodes'.DS, |
|
464 | + EE_LIBRARIES.'qtips'.DS, |
|
465 | + EE_LIBRARIES.'payment_methods'.DS, |
|
466 | + EE_LIBRARIES.'messages'.DS.'defaults'.DS, |
|
467 | 467 | ); |
468 | 468 | // retrieve instantiated class |
469 | 469 | return $this->_load($paths, 'EE_', $class_name, 'lib', $arguments, false, $cache, $load_only); |
@@ -502,10 +502,10 @@ discard block |
||
502 | 502 | public function load_model_class($class_name, $arguments = array(), $load_only = true) |
503 | 503 | { |
504 | 504 | $paths = array( |
505 | - EE_MODELS . 'fields' . DS, |
|
506 | - EE_MODELS . 'helpers' . DS, |
|
507 | - EE_MODELS . 'relations' . DS, |
|
508 | - EE_MODELS . 'strategies' . DS, |
|
505 | + EE_MODELS.'fields'.DS, |
|
506 | + EE_MODELS.'helpers'.DS, |
|
507 | + EE_MODELS.'relations'.DS, |
|
508 | + EE_MODELS.'strategies'.DS, |
|
509 | 509 | ); |
510 | 510 | // retrieve instantiated class |
511 | 511 | return $this->_load($paths, 'EE_', $class_name, '', $arguments, false, true, $load_only); |
@@ -592,7 +592,7 @@ discard block |
||
592 | 592 | $class_name = $this->_dependency_map->get_alias($class_name); |
593 | 593 | if ( ! class_exists($class_name)) { |
594 | 594 | // maybe the class is registered with a preceding \ |
595 | - $class_name = strpos($class_name, '\\') !== 0 ? '\\' . $class_name : $class_name; |
|
595 | + $class_name = strpos($class_name, '\\') !== 0 ? '\\'.$class_name : $class_name; |
|
596 | 596 | // still doesn't exist ? |
597 | 597 | if ( ! class_exists($class_name)) { |
598 | 598 | return null; |
@@ -659,7 +659,7 @@ discard block |
||
659 | 659 | // make sure $class_prefix is uppercase |
660 | 660 | $class_prefix = strtoupper(trim($class_prefix)); |
661 | 661 | // add class prefix ONCE!!! |
662 | - $class_name = $class_prefix . str_replace($class_prefix, '', $class_name); |
|
662 | + $class_name = $class_prefix.str_replace($class_prefix, '', $class_name); |
|
663 | 663 | } |
664 | 664 | $class_name = $this->_dependency_map->get_alias($class_name); |
665 | 665 | $class_exists = class_exists($class_name, false); |
@@ -722,8 +722,8 @@ discard block |
||
722 | 722 | return $this; |
723 | 723 | } |
724 | 724 | // have to specify something, but not anything that will conflict |
725 | - $class_abbreviation = isset($this->_class_abbreviations[ $class_name ]) |
|
726 | - ? $this->_class_abbreviations[ $class_name ] |
|
725 | + $class_abbreviation = isset($this->_class_abbreviations[$class_name]) |
|
726 | + ? $this->_class_abbreviations[$class_name] |
|
727 | 727 | : 'FANCY_BATMAN_PANTS'; |
728 | 728 | $class_name = str_replace('\\', '_', $class_name); |
729 | 729 | // check if class has already been loaded, and return it if it has been |
@@ -754,8 +754,8 @@ discard block |
||
754 | 754 | public function clear_cached_class($class_name, $addon = false) |
755 | 755 | { |
756 | 756 | // have to specify something, but not anything that will conflict |
757 | - $class_abbreviation = isset($this->_class_abbreviations[ $class_name ]) |
|
758 | - ? $this->_class_abbreviations[ $class_name ] |
|
757 | + $class_abbreviation = isset($this->_class_abbreviations[$class_name]) |
|
758 | + ? $this->_class_abbreviations[$class_name] |
|
759 | 759 | : 'FANCY_BATMAN_PANTS'; |
760 | 760 | $class_name = str_replace('\\', '_', $class_name); |
761 | 761 | // check if class has already been loaded, and return it if it has been |
@@ -800,9 +800,9 @@ discard block |
||
800 | 800 | // convert all separators to proper DS, if no filepath, then use EE_CLASSES |
801 | 801 | $file_path = $file_path ? str_replace(array('/', '\\'), DS, $file_path) : EE_CLASSES; |
802 | 802 | // prep file type |
803 | - $type = ! empty($type) ? trim($type, '.') . '.' : ''; |
|
803 | + $type = ! empty($type) ? trim($type, '.').'.' : ''; |
|
804 | 804 | // build full file path |
805 | - $file_paths[$key] = rtrim($file_path, DS) . DS . $class_name . '.' . $type . 'php'; |
|
805 | + $file_paths[$key] = rtrim($file_path, DS).DS.$class_name.'.'.$type.'php'; |
|
806 | 806 | //does the file exist and can be read ? |
807 | 807 | if (is_readable($file_paths[$key])) { |
808 | 808 | return $file_paths[$key]; |
@@ -834,12 +834,12 @@ discard block |
||
834 | 834 | //does the file exist and can it be read ? |
835 | 835 | if ( ! $path) { |
836 | 836 | // so sorry, can't find the file |
837 | - throw new EE_Error ( |
|
837 | + throw new EE_Error( |
|
838 | 838 | sprintf( |
839 | 839 | __('The %1$s file %2$s could not be located or is not readable due to file permissions. Please ensure that the following filepath(s) are correct: %3$s', 'event_espresso'), |
840 | 840 | trim($type, '.'), |
841 | 841 | $class_name, |
842 | - '<br />' . implode(',<br />', $file_paths) |
|
842 | + '<br />'.implode(',<br />', $file_paths) |
|
843 | 843 | ) |
844 | 844 | ); |
845 | 845 | } |
@@ -880,8 +880,8 @@ discard block |
||
880 | 880 | $legacy_parent_class_map = array( |
881 | 881 | 'EE_Payment_Processor' => 'core/business/EE_Processor_Base.class.php' |
882 | 882 | ); |
883 | - if(isset($legacy_parent_class_map[$class_name])) { |
|
884 | - require_once EE_PLUGIN_DIR_PATH . $legacy_parent_class_map[$class_name]; |
|
883 | + if (isset($legacy_parent_class_map[$class_name])) { |
|
884 | + require_once EE_PLUGIN_DIR_PATH.$legacy_parent_class_map[$class_name]; |
|
885 | 885 | } |
886 | 886 | } catch (Exception $exception) { |
887 | 887 | } |
@@ -38,217 +38,217 @@ |
||
38 | 38 | * @since 4.0 |
39 | 39 | */ |
40 | 40 | if (function_exists('espresso_version')) { |
41 | - if (! function_exists('espresso_duplicate_plugin_error')) { |
|
42 | - /** |
|
43 | - * espresso_duplicate_plugin_error |
|
44 | - * displays if more than one version of EE is activated at the same time |
|
45 | - */ |
|
46 | - function espresso_duplicate_plugin_error() |
|
47 | - { |
|
48 | - ?> |
|
41 | + if (! function_exists('espresso_duplicate_plugin_error')) { |
|
42 | + /** |
|
43 | + * espresso_duplicate_plugin_error |
|
44 | + * displays if more than one version of EE is activated at the same time |
|
45 | + */ |
|
46 | + function espresso_duplicate_plugin_error() |
|
47 | + { |
|
48 | + ?> |
|
49 | 49 | <div class="error"> |
50 | 50 | <p> |
51 | 51 | <?php |
52 | - 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 | - ); ?> |
|
52 | + 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 | + ); ?> |
|
56 | 56 | </p> |
57 | 57 | </div> |
58 | 58 | <?php |
59 | - espresso_deactivate_plugin(plugin_basename(__FILE__)); |
|
60 | - } |
|
61 | - } |
|
62 | - add_action('admin_notices', 'espresso_duplicate_plugin_error', 1); |
|
59 | + espresso_deactivate_plugin(plugin_basename(__FILE__)); |
|
60 | + } |
|
61 | + } |
|
62 | + add_action('admin_notices', 'espresso_duplicate_plugin_error', 1); |
|
63 | 63 | |
64 | 64 | } else { |
65 | - define('EE_MIN_PHP_VER_REQUIRED', '5.3.9'); |
|
66 | - if (! version_compare(PHP_VERSION, EE_MIN_PHP_VER_REQUIRED, '>=')) { |
|
67 | - /** |
|
68 | - * espresso_minimum_php_version_error |
|
69 | - * |
|
70 | - * @return void |
|
71 | - */ |
|
72 | - function espresso_minimum_php_version_error() |
|
73 | - { |
|
74 | - ?> |
|
65 | + define('EE_MIN_PHP_VER_REQUIRED', '5.3.9'); |
|
66 | + if (! version_compare(PHP_VERSION, EE_MIN_PHP_VER_REQUIRED, '>=')) { |
|
67 | + /** |
|
68 | + * espresso_minimum_php_version_error |
|
69 | + * |
|
70 | + * @return void |
|
71 | + */ |
|
72 | + function espresso_minimum_php_version_error() |
|
73 | + { |
|
74 | + ?> |
|
75 | 75 | <div class="error"> |
76 | 76 | <p> |
77 | 77 | <?php |
78 | - printf( |
|
79 | - esc_html__( |
|
80 | - '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.', |
|
81 | - 'event_espresso' |
|
82 | - ), |
|
83 | - EE_MIN_PHP_VER_REQUIRED, |
|
84 | - PHP_VERSION, |
|
85 | - '<br/>', |
|
86 | - '<a href="http://php.net/downloads.php">http://php.net/downloads.php</a>' |
|
87 | - ); |
|
88 | - ?> |
|
78 | + printf( |
|
79 | + esc_html__( |
|
80 | + '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.', |
|
81 | + 'event_espresso' |
|
82 | + ), |
|
83 | + EE_MIN_PHP_VER_REQUIRED, |
|
84 | + PHP_VERSION, |
|
85 | + '<br/>', |
|
86 | + '<a href="http://php.net/downloads.php">http://php.net/downloads.php</a>' |
|
87 | + ); |
|
88 | + ?> |
|
89 | 89 | </p> |
90 | 90 | </div> |
91 | 91 | <?php |
92 | - espresso_deactivate_plugin(plugin_basename(__FILE__)); |
|
93 | - } |
|
92 | + espresso_deactivate_plugin(plugin_basename(__FILE__)); |
|
93 | + } |
|
94 | 94 | |
95 | - add_action('admin_notices', 'espresso_minimum_php_version_error', 1); |
|
96 | - } else { |
|
97 | - define('EVENT_ESPRESSO_MAIN_FILE', __FILE__); |
|
98 | - /** |
|
99 | - * espresso_version |
|
100 | - * Returns the plugin version |
|
101 | - * |
|
102 | - * @return string |
|
103 | - */ |
|
104 | - function espresso_version() |
|
105 | - { |
|
106 | - return apply_filters('FHEE__espresso__espresso_version', '4.9.46.rc.004'); |
|
107 | - } |
|
95 | + add_action('admin_notices', 'espresso_minimum_php_version_error', 1); |
|
96 | + } else { |
|
97 | + define('EVENT_ESPRESSO_MAIN_FILE', __FILE__); |
|
98 | + /** |
|
99 | + * espresso_version |
|
100 | + * Returns the plugin version |
|
101 | + * |
|
102 | + * @return string |
|
103 | + */ |
|
104 | + function espresso_version() |
|
105 | + { |
|
106 | + return apply_filters('FHEE__espresso__espresso_version', '4.9.46.rc.004'); |
|
107 | + } |
|
108 | 108 | |
109 | - /** |
|
110 | - * espresso_plugin_activation |
|
111 | - * adds a wp-option to indicate that EE has been activated via the WP admin plugins page |
|
112 | - */ |
|
113 | - function espresso_plugin_activation() |
|
114 | - { |
|
115 | - update_option('ee_espresso_activation', true); |
|
116 | - } |
|
109 | + /** |
|
110 | + * espresso_plugin_activation |
|
111 | + * adds a wp-option to indicate that EE has been activated via the WP admin plugins page |
|
112 | + */ |
|
113 | + function espresso_plugin_activation() |
|
114 | + { |
|
115 | + update_option('ee_espresso_activation', true); |
|
116 | + } |
|
117 | 117 | |
118 | - register_activation_hook(EVENT_ESPRESSO_MAIN_FILE, 'espresso_plugin_activation'); |
|
119 | - /** |
|
120 | - * espresso_load_error_handling |
|
121 | - * this function loads EE's class for handling exceptions and errors |
|
122 | - */ |
|
123 | - function espresso_load_error_handling() |
|
124 | - { |
|
125 | - static $error_handling_loaded = false; |
|
126 | - if ($error_handling_loaded) { |
|
127 | - return; |
|
128 | - } |
|
129 | - // load debugging tools |
|
130 | - if (WP_DEBUG === true && is_readable(EE_HELPERS . 'EEH_Debug_Tools.helper.php')) { |
|
131 | - require_once(EE_HELPERS . 'EEH_Debug_Tools.helper.php'); |
|
132 | - \EEH_Debug_Tools::instance(); |
|
133 | - } |
|
134 | - // load error handling |
|
135 | - if (is_readable(EE_CORE . 'EE_Error.core.php')) { |
|
136 | - require_once(EE_CORE . 'EE_Error.core.php'); |
|
137 | - } else { |
|
138 | - wp_die(esc_html__('The EE_Error core class could not be loaded.', 'event_espresso')); |
|
139 | - } |
|
140 | - $error_handling_loaded = true; |
|
141 | - } |
|
118 | + register_activation_hook(EVENT_ESPRESSO_MAIN_FILE, 'espresso_plugin_activation'); |
|
119 | + /** |
|
120 | + * espresso_load_error_handling |
|
121 | + * this function loads EE's class for handling exceptions and errors |
|
122 | + */ |
|
123 | + function espresso_load_error_handling() |
|
124 | + { |
|
125 | + static $error_handling_loaded = false; |
|
126 | + if ($error_handling_loaded) { |
|
127 | + return; |
|
128 | + } |
|
129 | + // load debugging tools |
|
130 | + if (WP_DEBUG === true && is_readable(EE_HELPERS . 'EEH_Debug_Tools.helper.php')) { |
|
131 | + require_once(EE_HELPERS . 'EEH_Debug_Tools.helper.php'); |
|
132 | + \EEH_Debug_Tools::instance(); |
|
133 | + } |
|
134 | + // load error handling |
|
135 | + if (is_readable(EE_CORE . 'EE_Error.core.php')) { |
|
136 | + require_once(EE_CORE . 'EE_Error.core.php'); |
|
137 | + } else { |
|
138 | + wp_die(esc_html__('The EE_Error core class could not be loaded.', 'event_espresso')); |
|
139 | + } |
|
140 | + $error_handling_loaded = true; |
|
141 | + } |
|
142 | 142 | |
143 | - /** |
|
144 | - * espresso_load_required |
|
145 | - * given a class name and path, this function will load that file or throw an exception |
|
146 | - * |
|
147 | - * @param string $classname |
|
148 | - * @param string $full_path_to_file |
|
149 | - * @throws EE_Error |
|
150 | - */ |
|
151 | - function espresso_load_required($classname, $full_path_to_file) |
|
152 | - { |
|
153 | - if (is_readable($full_path_to_file)) { |
|
154 | - require_once($full_path_to_file); |
|
155 | - } else { |
|
156 | - throw new \EE_Error ( |
|
157 | - sprintf( |
|
158 | - esc_html__( |
|
159 | - 'The %s class file could not be located or is not readable due to file permissions.', |
|
160 | - 'event_espresso' |
|
161 | - ), |
|
162 | - $classname |
|
163 | - ) |
|
164 | - ); |
|
165 | - } |
|
166 | - } |
|
143 | + /** |
|
144 | + * espresso_load_required |
|
145 | + * given a class name and path, this function will load that file or throw an exception |
|
146 | + * |
|
147 | + * @param string $classname |
|
148 | + * @param string $full_path_to_file |
|
149 | + * @throws EE_Error |
|
150 | + */ |
|
151 | + function espresso_load_required($classname, $full_path_to_file) |
|
152 | + { |
|
153 | + if (is_readable($full_path_to_file)) { |
|
154 | + require_once($full_path_to_file); |
|
155 | + } else { |
|
156 | + throw new \EE_Error ( |
|
157 | + sprintf( |
|
158 | + esc_html__( |
|
159 | + 'The %s class file could not be located or is not readable due to file permissions.', |
|
160 | + 'event_espresso' |
|
161 | + ), |
|
162 | + $classname |
|
163 | + ) |
|
164 | + ); |
|
165 | + } |
|
166 | + } |
|
167 | 167 | |
168 | - /** |
|
169 | - * @since 4.9.27 |
|
170 | - * @throws \EE_Error |
|
171 | - * @throws \EventEspresso\core\exceptions\InvalidInterfaceException |
|
172 | - * @throws \EventEspresso\core\exceptions\InvalidEntityException |
|
173 | - * @throws \EventEspresso\core\exceptions\InvalidIdentifierException |
|
174 | - * @throws \EventEspresso\core\exceptions\InvalidClassException |
|
175 | - * @throws \EventEspresso\core\exceptions\InvalidDataTypeException |
|
176 | - * @throws \EventEspresso\core\services\container\exceptions\ServiceExistsException |
|
177 | - * @throws \EventEspresso\core\services\container\exceptions\ServiceNotFoundException |
|
178 | - * @throws \OutOfBoundsException |
|
179 | - */ |
|
180 | - function bootstrap_espresso() |
|
181 | - { |
|
182 | - require_once(plugin_dir_path(EVENT_ESPRESSO_MAIN_FILE) . 'core/espresso_definitions.php'); |
|
183 | - try { |
|
184 | - espresso_load_error_handling(); |
|
185 | - espresso_load_required( |
|
186 | - 'EEH_Base', |
|
187 | - EE_CORE . 'helpers' . DS . 'EEH_Base.helper.php' |
|
188 | - ); |
|
189 | - espresso_load_required( |
|
190 | - 'EEH_File', |
|
191 | - EE_CORE . 'interfaces' . DS . 'EEHI_File.interface.php' |
|
192 | - ); |
|
193 | - espresso_load_required( |
|
194 | - 'EEH_File', |
|
195 | - EE_CORE . 'helpers' . DS . 'EEH_File.helper.php' |
|
196 | - ); |
|
197 | - espresso_load_required( |
|
198 | - 'EEH_Array', |
|
199 | - EE_CORE . 'helpers' . DS . 'EEH_Array.helper.php' |
|
200 | - ); |
|
201 | - // instantiate and configure PSR4 autoloader |
|
202 | - espresso_load_required( |
|
203 | - 'Psr4Autoloader', |
|
204 | - EE_CORE . 'Psr4Autoloader.php' |
|
205 | - ); |
|
206 | - espresso_load_required( |
|
207 | - 'EE_Psr4AutoloaderInit', |
|
208 | - EE_CORE . 'EE_Psr4AutoloaderInit.core.php' |
|
209 | - ); |
|
210 | - $AutoloaderInit = new EE_Psr4AutoloaderInit(); |
|
211 | - $AutoloaderInit->initializeAutoloader(); |
|
212 | - espresso_load_required( |
|
213 | - 'EE_Request', |
|
214 | - EE_CORE . 'request_stack' . DS . 'EE_Request.core.php' |
|
215 | - ); |
|
216 | - espresso_load_required( |
|
217 | - 'EE_Response', |
|
218 | - EE_CORE . 'request_stack' . DS . 'EE_Response.core.php' |
|
219 | - ); |
|
220 | - espresso_load_required( |
|
221 | - 'EE_Bootstrap', |
|
222 | - EE_CORE . 'EE_Bootstrap.core.php' |
|
223 | - ); |
|
224 | - // bootstrap EE and the request stack |
|
225 | - new EE_Bootstrap( |
|
226 | - new EE_Request($_GET, $_POST, $_COOKIE), |
|
227 | - new EE_Response() |
|
228 | - ); |
|
229 | - } catch (Exception $e) { |
|
230 | - require_once EE_CORE . 'exceptions.' . DS . 'ExceptionStackTraceDisplay.php'; |
|
231 | - new EventEspresso\core\exceptions\ExceptionStackTraceDisplay($e); |
|
232 | - } |
|
233 | - } |
|
234 | - bootstrap_espresso(); |
|
235 | - } |
|
168 | + /** |
|
169 | + * @since 4.9.27 |
|
170 | + * @throws \EE_Error |
|
171 | + * @throws \EventEspresso\core\exceptions\InvalidInterfaceException |
|
172 | + * @throws \EventEspresso\core\exceptions\InvalidEntityException |
|
173 | + * @throws \EventEspresso\core\exceptions\InvalidIdentifierException |
|
174 | + * @throws \EventEspresso\core\exceptions\InvalidClassException |
|
175 | + * @throws \EventEspresso\core\exceptions\InvalidDataTypeException |
|
176 | + * @throws \EventEspresso\core\services\container\exceptions\ServiceExistsException |
|
177 | + * @throws \EventEspresso\core\services\container\exceptions\ServiceNotFoundException |
|
178 | + * @throws \OutOfBoundsException |
|
179 | + */ |
|
180 | + function bootstrap_espresso() |
|
181 | + { |
|
182 | + require_once(plugin_dir_path(EVENT_ESPRESSO_MAIN_FILE) . 'core/espresso_definitions.php'); |
|
183 | + try { |
|
184 | + espresso_load_error_handling(); |
|
185 | + espresso_load_required( |
|
186 | + 'EEH_Base', |
|
187 | + EE_CORE . 'helpers' . DS . 'EEH_Base.helper.php' |
|
188 | + ); |
|
189 | + espresso_load_required( |
|
190 | + 'EEH_File', |
|
191 | + EE_CORE . 'interfaces' . DS . 'EEHI_File.interface.php' |
|
192 | + ); |
|
193 | + espresso_load_required( |
|
194 | + 'EEH_File', |
|
195 | + EE_CORE . 'helpers' . DS . 'EEH_File.helper.php' |
|
196 | + ); |
|
197 | + espresso_load_required( |
|
198 | + 'EEH_Array', |
|
199 | + EE_CORE . 'helpers' . DS . 'EEH_Array.helper.php' |
|
200 | + ); |
|
201 | + // instantiate and configure PSR4 autoloader |
|
202 | + espresso_load_required( |
|
203 | + 'Psr4Autoloader', |
|
204 | + EE_CORE . 'Psr4Autoloader.php' |
|
205 | + ); |
|
206 | + espresso_load_required( |
|
207 | + 'EE_Psr4AutoloaderInit', |
|
208 | + EE_CORE . 'EE_Psr4AutoloaderInit.core.php' |
|
209 | + ); |
|
210 | + $AutoloaderInit = new EE_Psr4AutoloaderInit(); |
|
211 | + $AutoloaderInit->initializeAutoloader(); |
|
212 | + espresso_load_required( |
|
213 | + 'EE_Request', |
|
214 | + EE_CORE . 'request_stack' . DS . 'EE_Request.core.php' |
|
215 | + ); |
|
216 | + espresso_load_required( |
|
217 | + 'EE_Response', |
|
218 | + EE_CORE . 'request_stack' . DS . 'EE_Response.core.php' |
|
219 | + ); |
|
220 | + espresso_load_required( |
|
221 | + 'EE_Bootstrap', |
|
222 | + EE_CORE . 'EE_Bootstrap.core.php' |
|
223 | + ); |
|
224 | + // bootstrap EE and the request stack |
|
225 | + new EE_Bootstrap( |
|
226 | + new EE_Request($_GET, $_POST, $_COOKIE), |
|
227 | + new EE_Response() |
|
228 | + ); |
|
229 | + } catch (Exception $e) { |
|
230 | + require_once EE_CORE . 'exceptions.' . DS . 'ExceptionStackTraceDisplay.php'; |
|
231 | + new EventEspresso\core\exceptions\ExceptionStackTraceDisplay($e); |
|
232 | + } |
|
233 | + } |
|
234 | + bootstrap_espresso(); |
|
235 | + } |
|
236 | 236 | } |
237 | 237 | if (! function_exists('espresso_deactivate_plugin')) { |
238 | - /** |
|
239 | - * deactivate_plugin |
|
240 | - * usage: espresso_deactivate_plugin( plugin_basename( __FILE__ )); |
|
241 | - * |
|
242 | - * @access public |
|
243 | - * @param string $plugin_basename - the results of plugin_basename( __FILE__ ) for the plugin's main file |
|
244 | - * @return void |
|
245 | - */ |
|
246 | - function espresso_deactivate_plugin($plugin_basename = '') |
|
247 | - { |
|
248 | - if (! function_exists('deactivate_plugins')) { |
|
249 | - require_once(ABSPATH . 'wp-admin/includes/plugin.php'); |
|
250 | - } |
|
251 | - unset($_GET['activate'], $_REQUEST['activate']); |
|
252 | - deactivate_plugins($plugin_basename); |
|
253 | - } |
|
238 | + /** |
|
239 | + * deactivate_plugin |
|
240 | + * usage: espresso_deactivate_plugin( plugin_basename( __FILE__ )); |
|
241 | + * |
|
242 | + * @access public |
|
243 | + * @param string $plugin_basename - the results of plugin_basename( __FILE__ ) for the plugin's main file |
|
244 | + * @return void |
|
245 | + */ |
|
246 | + function espresso_deactivate_plugin($plugin_basename = '') |
|
247 | + { |
|
248 | + if (! function_exists('deactivate_plugins')) { |
|
249 | + require_once(ABSPATH . 'wp-admin/includes/plugin.php'); |
|
250 | + } |
|
251 | + unset($_GET['activate'], $_REQUEST['activate']); |
|
252 | + deactivate_plugins($plugin_basename); |
|
253 | + } |
|
254 | 254 | } |