Completed
Branch BUG-10381-asset-loading (189bf4)
by
unknown
13:54
created

EE_Front_Controller   F

Complexity

Total Complexity 74

Size/Duplication

Total Lines 608
Duplicated Lines 0.82 %

Coupling/Cohesion

Components 1
Dependencies 15

Importance

Changes 0
Metric Value
dl 5
loc 608
rs 2.3428
c 0
b 0
f 0
wmc 74
lcom 1
cbo 15

20 Methods

Rating   Name   Duplication   Size   Complexity  
B __construct() 0 42 2
A Request_Handler() 0 4 1
A Module_Request_Router() 0 4 1
A getLegacyShortcodesManager() 0 4 1
A filter_wp_comments() 0 11 3
A employ_CPT_Strategy() 0 6 2
A maybe_force_admin_ajax_ssl() 0 7 3
A wp_loaded() 0 3 1
A get_request() 0 6 1
B pre_get_posts() 0 22 5
A wp() 0 3 1
A get_header() 0 15 4
C espresso_widgets_in_active_sidebars() 0 23 9
F wp_enqueue_scripts() 5 118 17
B header_meta_tag() 0 26 4
B wp_print_scripts() 0 12 5
B display_errors() 0 18 7
A template_include() 0 11 4
A get_selected_template() 0 4 2
A initialize_shortcode() 0 12 1

How to fix   Duplicated Code    Complexity   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

Complex Class

 Tip:   Before tackling complexity, make sure that you eliminate any duplication first. This often can reduce the size of classes significantly.

Complex classes like EE_Front_Controller often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes. You can also have a look at the cohesion graph to spot any un-connected, or weakly-connected components.

Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.

While breaking up the class, it is a good idea to analyze how other classes use EE_Front_Controller, and based on these observations, apply Extract Interface, too.

1
<?php
2
use EventEspresso\core\services\shortcodes\LegacyShortcodesManager;
3
use EventEspresso\widgets\EspressoWidget;
4
5
if ( ! defined('EVENT_ESPRESSO_VERSION')) {
6
    exit('No direct script access allowed');
7
}
8
9
/**
10
 * Event Espresso
11
 * Event Registration and Management Plugin for WordPress
12
 * @ package            Event Espresso
13
 * @ author            Seth Shoultes
14
 * @ copyright        (c) 2008-2011 Event Espresso  All Rights Reserved.
15
 * @ license            http://eventespresso.com/support/terms-conditions/   * see Plugin Licensing *
16
 * @ link                    http://www.eventespresso.com
17
 * @ version            4.0
18
 * ------------------------------------------------------------------------
19
 * EE_Front_Controller
20
 *
21
 * @package               Event Espresso
22
 * @subpackage            core/
23
 * @author                Brent Christensen
24
 *                        ------------------------------------------------------------------------
25
 */
26
final class EE_Front_Controller
27
{
28
29
    /**
30
     * @var string $_template_path
31
     */
32
    private $_template_path;
33
34
    /**
35
     * @var string $_template
36
     */
37
    private $_template;
38
39
    /**
40
     * @type EE_Registry $Registry
41
     */
42
    protected $Registry;
43
44
    /**
45
     * @type EE_Request_Handler $Request_Handler
46
     */
47
    protected $Request_Handler;
48
49
    /**
50
     * @type EE_Module_Request_Router $Module_Request_Router
51
     */
52
    protected $Module_Request_Router;
53
54
55
    /**
56
     *    class constructor
57
     *    should fire after shortcode, module, addon, or other plugin's default priority init phases have run
58
     *
59
     * @access    public
60
     * @param \EE_Registry              $Registry
61
     * @param \EE_Request_Handler       $Request_Handler
62
     * @param \EE_Module_Request_Router $Module_Request_Router
63
     */
64
    public function __construct(
65
        EE_Registry $Registry,
66
        EE_Request_Handler $Request_Handler,
67
        EE_Module_Request_Router $Module_Request_Router
68
    ) {
69
        $this->Registry              = $Registry;
70
        $this->Request_Handler       = $Request_Handler;
71
        $this->Module_Request_Router = $Module_Request_Router;
72
        // determine how to integrate WP_Query with the EE models
73
        add_action('AHEE__EE_System__initialize', array($this, 'employ_CPT_Strategy'));
74
        // load other resources and begin to actually run shortcodes and modules
75
        add_action('wp_loaded', array($this, 'wp_loaded'), 5);
76
        // analyse the incoming WP request
77
        add_action('parse_request', array($this, 'get_request'), 1, 1);
78
        // process request with module factory
79
        add_action('pre_get_posts', array($this, 'pre_get_posts'), 10, 1);
80
        // before headers sent
81
        add_action('wp', array($this, 'wp'), 5);
82
        // after headers sent but before any markup is output,
83
        // primarily used to process any content shortcodes
84
        add_action('get_header', array($this, 'get_header'));
85
        // load css and js
86
        add_action('wp_enqueue_scripts', array($this, 'wp_enqueue_scripts'), 1);
87
        // header
88
        add_action('wp_head', array($this, 'header_meta_tag'), 5);
89
        add_action('wp_print_scripts', array($this, 'wp_print_scripts'), 10);
90
        add_filter('template_include', array($this, 'template_include'), 1);
91
        // display errors
92
        add_action('loop_start', array($this, 'display_errors'), 2);
93
        // the content
94
        // add_filter( 'the_content', array( $this, 'the_content' ), 5, 1 );
95
        //exclude our private cpt comments
96
        add_filter('comments_clauses', array($this, 'filter_wp_comments'), 10, 1);
97
        //make sure any ajax requests will respect the url schema when requests are made against admin-ajax.php (http:// or https://)
98
        add_filter('admin_url', array($this, 'maybe_force_admin_ajax_ssl'), 200, 1);
99
        // action hook EE
100
        do_action('AHEE__EE_Front_Controller__construct__done', $this);
101
        // for checking that browser cookies are enabled
102
        if (apply_filters('FHEE__EE_Front_Controller____construct__set_test_cookie', true)) {
103
            setcookie('ee_cookie_test', uniqid('ect',true), time() + DAY_IN_SECONDS, '/');
104
        }
105
    }
106
107
108
    /**
109
     * @return EE_Request_Handler
110
     */
111
    public function Request_Handler()
112
    {
113
        return $this->Request_Handler;
114
    }
115
116
117
    /**
118
     * @return EE_Module_Request_Router
119
     */
120
    public function Module_Request_Router()
121
    {
122
        return $this->Module_Request_Router;
123
    }
124
125
126
127
    /**
128
     * @return LegacyShortcodesManager
129
     */
130
    public function getLegacyShortcodesManager()
131
    {
132
        return EE_Config::getLegacyShortcodesManager();
133
    }
134
135
136
137
138
139
    /***********************************************        INIT ACTION HOOK         ***********************************************/
140
141
142
143
    /**
144
     * filter_wp_comments
145
     * This simply makes sure that any "private" EE CPTs do not have their comments show up in any wp comment
146
     * widgets/queries done on frontend
147
     *
148
     * @param  array $clauses array of comment clauses setup by WP_Comment_Query
149
     * @return array array of comment clauses with modifications.
150
     */
151
    public function filter_wp_comments($clauses)
152
    {
153
        global $wpdb;
154
        if (strpos($clauses['join'], $wpdb->posts) !== false) {
155
            $cpts = EE_Register_CPTs::get_private_CPTs();
156
            foreach ($cpts as $cpt => $details) {
157
                $clauses['where'] .= $wpdb->prepare(" AND $wpdb->posts.post_type != %s", $cpt);
158
            }
159
        }
160
        return $clauses;
161
    }
162
163
164
    /**
165
     *    employ_CPT_Strategy
166
     *
167
     * @access    public
168
     * @return    void
169
     */
170
    public function employ_CPT_Strategy()
171
    {
172
        if (apply_filters('FHEE__EE_Front_Controller__employ_CPT_Strategy', true)) {
173
            $this->Registry->load_core('CPT_Strategy');
174
        }
175
    }
176
177
178
    /**
179
     * this just makes sure that if the site is using ssl that we force that for any admin ajax calls from frontend
180
     *
181
     * @param  string $url incoming url
182
     * @return string         final assembled url
183
     */
184
    public function maybe_force_admin_ajax_ssl($url)
185
    {
186
        if (is_ssl() && preg_match('/admin-ajax.php/', $url)) {
187
            $url = str_replace('http://', 'https://', $url);
188
        }
189
        return $url;
190
    }
191
192
193
194
195
196
197
    /***********************************************        WP_LOADED ACTION HOOK         ***********************************************/
198
199
200
    /**
201
     *    wp_loaded - should fire after shortcode, module, addon, or other plugin's have been registered and their
202
     *    default priority init phases have run
203
     *
204
     * @access    public
205
     * @return    void
206
     */
207
    public function wp_loaded()
208
    {
209
    }
210
211
212
213
214
215
    /***********************************************        PARSE_REQUEST HOOK         ***********************************************/
216
    /**
217
     *    _get_request
218
     *
219
     * @access public
220
     * @param WP $WP
221
     * @return void
222
     */
223
    public function get_request(WP $WP)
224
    {
225
        do_action('AHEE__EE_Front_Controller__get_request__start');
226
        $this->Request_Handler->parse_request($WP);
227
        do_action('AHEE__EE_Front_Controller__get_request__complete');
228
    }
229
230
231
232
    /**
233
     *    pre_get_posts - basically a module factory for instantiating modules and selecting the final view template
234
     *
235
     * @access    public
236
     * @param   WP_Query $WP_Query
237
     * @return    void
238
     */
239
    public function pre_get_posts($WP_Query)
240
    {
241
        // only load Module_Request_Router if this is the main query
242
        if (
243
            $this->Module_Request_Router instanceof EE_Module_Request_Router
244
            && $WP_Query->is_main_query()
245
        ) {
246
            // cycle thru module routes
247
            while ($route = $this->Module_Request_Router->get_route($WP_Query)) {
248
                // determine module and method for route
249
                $module = $this->Module_Request_Router->resolve_route($route[0], $route[1]);
250
                if ($module instanceof EED_Module) {
251
                    // get registered view for route
252
                    $this->_template_path = $this->Module_Request_Router->get_view($route);
253
                    // grab module name
254
                    $module_name = $module->module_name();
255
                    // map the module to the module objects
256
                    $this->Registry->modules->{$module_name} = $module;
257
                }
258
            }
259
        }
260
    }
261
262
263
264
265
266
    /***********************************************        WP HOOK         ***********************************************/
267
268
269
    /**
270
     *    wp - basically last chance to do stuff before headers sent
271
     *
272
     * @access    public
273
     * @return    void
274
     */
275
    public function wp()
276
    {
277
    }
278
279
280
281
    /***********************     GET_HEADER, WP_ENQUEUE_SCRIPTS && WP_HEAD HOOK     ***********************/
282
283
284
285
    /**
286
     * callback for the WP "get_header" hook point
287
     * checks sidebars for EE widgets
288
     * loads resources and assets accordingly
289
     *
290
     * @return void
291
     */
292
    public function get_header()
293
    {
294
        global $wp_query;
295
        if (empty($wp_query->posts)){
296
            return;
297
        }
298
        // if we already know this is an espresso page, then load assets
299
        $load_assets = $this->Request_Handler->is_espresso_page();
300
        // if we are already loading assets then just move along, otherwise check for widgets
301
        $load_assets = $load_assets ? $load_assets : $this->espresso_widgets_in_active_sidebars();
302
        if ( $load_assets){
303
            add_filter('FHEE_load_css', '__return_true');
304
            add_filter('FHEE_load_js', '__return_true');
305
        }
306
    }
307
308
309
310
    /**
311
     * builds list of active widgets then scans active sidebars looking for them
312
     * returns true is an EE widget is found in an active sidebar
313
     * Please Note: this does NOT mean that the sidebar or widget
314
     * is actually in use in a given template, as that is unfortunately not known
315
     * until a sidebar and it's widgets are actually loaded
316
     *
317
     * @return boolean
318
     */
319
    private function espresso_widgets_in_active_sidebars()
320
    {
321
        $espresso_widgets = array();
322
        foreach ($this->Registry->widgets as $widget_class => $widget) {
323
            $id_base = EspressoWidget::getIdBase($widget_class);
324
            if (is_active_widget(false, false, $id_base)) {
325
                $espresso_widgets[] = $id_base;
326
            }
327
        }
328
        $all_sidebar_widgets = wp_get_sidebars_widgets();
329
        foreach ($all_sidebar_widgets as $sidebar_name => $sidebar_widgets) {
330
            if (is_array($sidebar_widgets) && ! empty($sidebar_widgets)) {
331
                foreach ($sidebar_widgets as $sidebar_widget) {
332
                    foreach ($espresso_widgets as $espresso_widget) {
333
                        if (strpos($sidebar_widget, $espresso_widget) !== false) {
334
                            return true;
335
                        }
336
                    }
337
                }
338
            }
339
        }
340
        return false;
341
    }
342
343
344
345
346
    /**
347
     *    wp_enqueue_scripts
348
     *
349
     * @access    public
350
     * @return    void
351
     */
352
    public function wp_enqueue_scripts()
353
    {
354
        // css is turned ON by default, but prior to the wp_enqueue_scripts hook, can be turned OFF  via:  add_filter( 'FHEE_load_css', '__return_false' );
355
        if (apply_filters('FHEE_load_css', false)) {
356
357
            $this->Registry->CFG->template_settings->enable_default_style = true;
358
            //Load the ThemeRoller styles if enabled
359
            if (isset($this->Registry->CFG->template_settings->enable_default_style) && $this->Registry->CFG->template_settings->enable_default_style) {
360
361
                //Load custom style sheet if available
362
                if (isset($this->Registry->CFG->template_settings->custom_style_sheet)) {
363
                    wp_register_style('espresso_custom_css',
364
                        EVENT_ESPRESSO_UPLOAD_URL . 'css/' . $this->Registry->CFG->template_settings->custom_style_sheet,
365
                        EVENT_ESPRESSO_VERSION);
366
                    wp_enqueue_style('espresso_custom_css');
367
                }
368
369
                if (is_readable(EVENT_ESPRESSO_UPLOAD_DIR . 'css/style.css')) {
370
                    wp_register_style('espresso_default', EVENT_ESPRESSO_UPLOAD_DIR . 'css/espresso_default.css',
371
                        array('dashicons'), EVENT_ESPRESSO_VERSION);
372
                } else {
373
                    wp_register_style('espresso_default', EE_GLOBAL_ASSETS_URL . 'css/espresso_default.css',
374
                        array('dashicons'), EVENT_ESPRESSO_VERSION);
375
                }
376
                wp_enqueue_style('espresso_default');
377
378 View Code Duplication
                if (is_readable(get_stylesheet_directory() . EE_Config::get_current_theme() . DS . 'style.css')) {
379
                    wp_register_style('espresso_style',
380
                        get_stylesheet_directory_uri() . EE_Config::get_current_theme() . DS . 'style.css',
381
                        array('dashicons', 'espresso_default'));
382
                } else {
383
                    wp_register_style('espresso_style',
384
                        EE_TEMPLATES_URL . EE_Config::get_current_theme() . DS . 'style.css',
385
                        array('dashicons', 'espresso_default'));
386
                }
387
388
            }
389
390
        }
391
392
        // js is turned ON by default, but prior to the wp_enqueue_scripts hook, can be turned OFF  via:  add_filter( 'FHEE_load_js', '__return_false' );
393
        if (apply_filters('FHEE_load_js', false)) {
394
395
            wp_enqueue_script('jquery');
396
            //let's make sure that all required scripts have been setup
397
            if (function_exists('wp_script_is') && ! wp_script_is('jquery')) {
398
                $msg = sprintf(
399
                    __('%sJquery is not loaded!%sEvent Espresso is unable to load Jquery due to a conflict with your theme or another plugin.',
400
                        'event_espresso'),
401
                    '<em><br />',
402
                    '</em>'
403
                );
404
                EE_Error::add_error($msg, __FILE__, __FUNCTION__, __LINE__);
405
            }
406
            // load core js
407
            wp_register_script('espresso_core', EE_GLOBAL_ASSETS_URL . 'scripts/espresso_core.js', array('jquery'),
408
                EVENT_ESPRESSO_VERSION, true);
409
            wp_enqueue_script('espresso_core');
410
            wp_localize_script('espresso_core', 'eei18n', EE_Registry::$i18n_js_strings);
411
412
        }
413
414
        //qtip is turned OFF by default, but prior to the wp_enqueue_scripts hook, can be turned back on again via: add_filter('FHEE_load_qtip', '__return_true' );
415
        if (apply_filters('FHEE_load_qtip', false)) {
416
            EEH_Qtip_Loader::instance()->register_and_enqueue();
417
        }
418
419
420
        //accounting.js library
421
        // @link http://josscrowcroft.github.io/accounting.js/
422
        if (apply_filters('FHEE_load_accounting_js', false)) {
423
            $acct_js = EE_THIRD_PARTY_URL . 'accounting/accounting.js';
424
            wp_register_script('ee-accounting', EE_GLOBAL_ASSETS_URL . 'scripts/ee-accounting-config.js',
425
                array('ee-accounting-core'), EVENT_ESPRESSO_VERSION, true);
426
            wp_register_script('ee-accounting-core', $acct_js, array('underscore'), '0.3.2', true);
427
            wp_enqueue_script('ee-accounting');
428
429
            $currency_config = array(
430
                'currency' => array(
431
                    'symbol'    => $this->Registry->CFG->currency->sign,
432
                    'format'    => array(
433
                        'pos'  => $this->Registry->CFG->currency->sign_b4 ? '%s%v' : '%v%s',
434
                        'neg'  => $this->Registry->CFG->currency->sign_b4 ? '- %s%v' : '- %v%s',
435
                        'zero' => $this->Registry->CFG->currency->sign_b4 ? '%s--' : '--%s',
436
                    ),
437
                    'decimal'   => $this->Registry->CFG->currency->dec_mrk,
438
                    'thousand'  => $this->Registry->CFG->currency->thsnds,
439
                    'precision' => $this->Registry->CFG->currency->dec_plc,
440
                ),
441
                'number'   => array(
442
                    'precision' => 0,
443
                    'thousand'  => $this->Registry->CFG->currency->thsnds,
444
                    'decimal'   => $this->Registry->CFG->currency->dec_mrk,
445
                ),
446
            );
447
            wp_localize_script('ee-accounting', 'EE_ACCOUNTING_CFG', $currency_config);
448
        }
449
450
        if ( ! function_exists('wp_head')) {
451
            $msg = sprintf(
452
                __('%sMissing wp_head() function.%sThe WordPress function wp_head() seems to be missing in your theme. Please contact the theme developer to make sure this is fixed before using Event Espresso.',
453
                    'event_espresso'),
454
                '<em><br />',
455
                '</em>'
456
            );
457
            EE_Error::add_error($msg, __FILE__, __FUNCTION__, __LINE__);
458
        }
459
        if ( ! function_exists('wp_footer')) {
460
            $msg = sprintf(
461
                __('%sMissing wp_footer() function.%sThe WordPress function wp_footer() seems to be missing in your theme. Please contact the theme developer to make sure this is fixed before using Event Espresso.',
462
                    'event_espresso'),
463
                '<em><br />',
464
                '</em>'
465
            );
466
            EE_Error::add_error($msg, __FILE__, __FUNCTION__, __LINE__);
467
        }
468
469
    }
470
471
472
    /**
473
     *    header_meta_tag
474
     *
475
     * @access    public
476
     * @return    void
477
     */
478
    public function header_meta_tag()
479
    {
480
        print(
481
            apply_filters(
482
                'FHEE__EE_Front_Controller__header_meta_tag',
483
                '<meta name="generator" content="Event Espresso Version ' . EVENT_ESPRESSO_VERSION . "\" />\n")
484
        );
485
486
        //let's exclude all event type taxonomy term archive pages from search engine indexing
487
        //@see https://events.codebasehq.com/projects/event-espresso/tickets/10249
488
        //also exclude all critical pages from indexing
489
        if (
490
            (
491
                is_tax('espresso_event_type')
492
                && get_option( 'blog_public' ) !== '0'
493
            )
494
            || is_page(EE_Registry::instance()->CFG->core->get_critical_pages_array())
495
        ) {
496
            print(
497
                apply_filters(
498
                    'FHEE__EE_Front_Controller__header_meta_tag__noindex_for_event_type',
499
                    '<meta name="robots" content="noindex,follow" />' . "\n"
500
                )
501
            );
502
        }
503
    }
504
505
506
507
    /**
508
     * wp_print_scripts
509
     *
510
     * @return void
511
     */
512
    public function wp_print_scripts()
513
    {
514
        global $post;
515
        if (
516
            get_post_type() === 'espresso_events' 
517
            && is_singular() 
518
            && isset($post->EE_Event)
519
            && $post->EE_Event instanceof EE_Event
520
        ) {
521
            \EEH_Schema::add_json_linked_data_for_event($post->EE_Event);
522
        }
523
    }
524
525
526
527
528
    /***********************************************        THE_CONTENT FILTER HOOK         **********************************************
529
530
531
532
    // /**
533
    //  *    the_content
534
    //  *
535
    //  * @access    public
536
    //  * @param   $the_content
537
    //  * @return    string
538
    //  */
539
    // public function the_content( $the_content ) {
540
    // 	// nothing gets loaded at this point unless other systems turn this hookpoint on by using:  add_filter( 'FHEE_run_EE_the_content', '__return_true' );
541
    // 	if ( apply_filters( 'FHEE_run_EE_the_content', FALSE ) ) {
542
    // 	}
543
    // 	return $the_content;
544
    // }
545
546
547
548
    /***********************************************        WP_FOOTER         ***********************************************/
549
550
551
    /**
552
     * display_errors
553
     *
554
     * @access public
555
     * @return void
556
     */
557
    public function display_errors()
558
    {
559
        static $shown_already = false;
560
        do_action('AHEE__EE_Front_Controller__display_errors__begin');
561
        if (
562
            ! $shown_already
563
            && apply_filters('FHEE__EE_Front_Controller__display_errors', true)
564
            && is_main_query()
565
            && ! is_feed()
566
            && in_the_loop()
567
            && $this->Request_Handler->is_espresso_page()
568
        ) {
569
            echo EE_Error::get_notices();
570
            $shown_already = true;
571
            EEH_Template::display_template(EE_TEMPLATES . 'espresso-ajax-notices.template.php');
572
        }
573
        do_action('AHEE__EE_Front_Controller__display_errors__end');
574
    }
575
576
577
578
579
580
    /***********************************************        UTILITIES         ***********************************************/
581
    /**
582
     *    template_include
583
     *
584
     * @access    public
585
     * @param   string $template_include_path
586
     * @return    string
587
     */
588
    public function template_include($template_include_path = null)
589
    {
590
        if ($this->Request_Handler->is_espresso_page()) {
591
            $this->_template_path = ! empty($this->_template_path) ? basename($this->_template_path) : basename($template_include_path);
592
            $template_path        = EEH_Template::locate_template($this->_template_path, array(), false);
593
            $this->_template_path = ! empty($template_path) ? $template_path : $template_include_path;
594
            $this->_template      = basename($this->_template_path);
595
            return $this->_template_path;
596
        }
597
        return $template_include_path;
598
    }
599
600
601
    /**
602
     *    get_selected_template
603
     *
604
     * @access    public
605
     * @param bool $with_path
606
     * @return    string
607
     */
608
    public function get_selected_template($with_path = false)
609
    {
610
        return $with_path ? $this->_template_path : $this->_template;
611
    }
612
613
614
615
    /**
616
     * @deprecated 4.9.26
617
     * @param string $shortcode_class
618
     * @param \WP    $wp
619
     */
620
    public function initialize_shortcode($shortcode_class = '', WP $wp = null)
621
    {
622
        \EE_Error::doing_it_wrong(
623
            __METHOD__,
624
            __(
625
                'Usage is deprecated. Please use \EventEspresso\core\services\shortcodes\LegacyShortcodesManager::initializeShortcode() instead.',
626
                'event_espresso'
627
            ),
628
            '4.9.26'
629
        );
630
        $this->getLegacyShortcodesManager()->initializeShortcode($shortcode_class, $wp);
631
    }
632
633
}
634
// End of file EE_Front_Controller.core.php
635
// Location: /core/EE_Front_Controller.core.php
636