Completed
Branch FET/9575/invisible-recaptcha (a1de93)
by
unknown
80:39 queued 68:16
created

EE_Request::matches()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 2
nc 1
nop 1
dl 0
loc 4
rs 10
c 0
b 0
f 0
1
<?php
2
3
use EventEspresso\core\interfaces\InterminableInterface;
4
5
defined('EVENT_ESPRESSO_VERSION') || exit('No direct script access allowed');
6
7
8
9
/**
10
 * class EE_Request
11
 *
12
 * @package     Event Espresso
13
 * @subpackage  /core/
14
 * @author      Brent Christensen
15
 */
16
class EE_Request implements InterminableInterface
17
{
18
19
    /**
20
     * $_GET parameters
21
     *
22
     * @var array $_get
23
     */
24
    private $_get;
25
26
    /**
27
     * $_POST parameters
28
     *
29
     * @var    array $_post
30
     */
31
    private $_post;
32
33
    /**
34
     * $_COOKIE parameters
35
     *
36
     * @var array $_cookie
37
     */
38
    private $_cookie;
39
40
    /**
41
     * $_REQUEST parameters
42
     *
43
     * @var array $_params
44
     */
45
    private $_params;
46
47
    /**
48
     * whether current request is for the admin but NOT via AJAX
49
     *
50
     * @var boolean $admin
51
     */
52
    public $admin = false;
53
54
    /**
55
     * whether current request is via AJAX
56
     *
57
     * @var boolean $ajax
58
     */
59
    public $ajax = false;
60
61
    /**
62
     * whether current request is via AJAX from the frontend of the site
63
     *
64
     * @var boolean $front_ajax
65
     */
66
    public $front_ajax = false;
67
68
    /**
69
     * IP address for request
70
     *
71
     * @var string $_ip_address
72
     */
73
    private $_ip_address;
74
75
76
77
    /**
78
     * class constructor
79
     *
80
     * @access    public
81
     * @param array $get
82
     * @param array $post
83
     * @param array $cookie
84
     */
85
    public function __construct(array $get, array $post, array $cookie)
86
    {
87
        // grab request vars
88
        $this->_get    = $get;
89
        $this->_post   = $post;
90
        $this->_cookie = $cookie;
91
        $this->_params = array_merge($this->_get, $this->_post);
92
        // AJAX ???
93
        $this->ajax       = defined('DOING_AJAX') && DOING_AJAX;
94
        $this->front_ajax = $this->ajax
95
                            && $this->is_set('ee_front_ajax')
96
                            && filter_var($this->get('ee_front_ajax'), FILTER_VALIDATE_BOOLEAN);
97
        $this->admin      = is_admin() && ! $this->ajax;
98
        // grab user IP
99
        $this->_ip_address = $this->_visitor_ip();
100
    }
101
102
103
104
    /**
105
     * @return array
106
     */
107
    public function get_params()
108
    {
109
        return $this->_get;
110
    }
111
112
113
114
    /**
115
     * @return array
116
     */
117
    public function post_params()
118
    {
119
        return $this->_post;
120
    }
121
122
123
124
    /**
125
     * @return array
126
     */
127
    public function cookie_params()
128
    {
129
        return $this->_cookie;
130
    }
131
132
133
134
    /**
135
     * returns contents of $_REQUEST
136
     *
137
     * @return array
138
     */
139
    public function params()
140
    {
141
        return $this->_params;
142
    }
143
144
145
146
    /**
147
     * @param      $key
148
     * @param      $value
149
     * @param bool $override_ee
150
     * @return    void
151
     */
152
    public function set($key, $value, $override_ee = false)
153
    {
154
        // don't allow "ee" to be overwritten unless explicitly instructed to do so
155
        if (
156
            $key !== 'ee'
157
            || ($key === 'ee' && empty($this->_params['ee']))
158
            || ($key === 'ee' && ! empty($this->_params['ee']) && $override_ee)
159
        ) {
160
            $this->_params[$key] = $value;
161
        }
162
    }
163
164
165
166
    /**
167
     * returns   the value for a request param if the given key exists
168
     *
169
     * @param       $key
170
     * @param null|mixed  $default
171
     * @return mixed
172
     */
173
    public function get($key, $default = null)
174
    {
175
        return $this->request_parameter_drill_down($key, $default, 'get');
176
    }
177
178
179
180
    /**
181
     * check if param exists
182
     *
183
     * @param       $key
184
     * @return bool
185
     */
186
    public function is_set($key)
187
    {
188
        return $this->request_parameter_drill_down($key);
189
    }
190
191
192
    /**
193
     * check if a request parameter exists whose key that matches the supplied wildcard pattern
194
     * and return the value for the first match found
195
     * wildcards can be either of the following:
196
     *      ? to represent a single character of any type
197
     *      * to represent one or more characters of any type
198
     *
199
     * @param string $pattern
200
     * @param null|mixed $default
201
     * @return false|int
202
     */
203
    public function getMatch($pattern, $default = null)
204
    {
205
        return $this->request_parameter_drill_down($pattern, $default, 'match');
206
    }
207
208
209
    /**
210
     * check if a request parameter exists whose key matches the supplied wildcard pattern
211
     * wildcards can be either of the following:
212
     *      ? to represent a single character of any type
213
     *      * to represent one or more characters of any type
214
     * returns true if a match is found or false if not
215
     *
216
     * @param string $pattern
217
     * @return false|int
218
     */
219
    public function matches($pattern)
220
    {
221
        return $this->request_parameter_drill_down($pattern, null, 'match') !== null;
222
    }
223
224
225
    /**
226
     * @see https://stackoverflow.com/questions/6163055/php-string-matching-with-wildcard
227
     * @param string $pattern           A string including wildcards to be converted to a regex pattern
228
     *                                  and used to search through the current request's parameter keys
229
     * @param array  $request_params    The array of request parameters to search through
230
     * @param mixed  $default           [optional] The value to be returned if no match is found.
231
     *                                  Default is null
232
     * @param string $return            [optional] Controls what kind of value is returned.
233
     *                                  Options are:
234
     *                                      'bool' will return true or false if match is found or not
235
     *                                      'key' will return the first key found that matches the supplied pattern
236
     *                                      'value' will return the value for the first request parameter
237
     *                                      whose key matches the supplied pattern
238
     *                                  Default is 'value'
239
     * @return boolean|string
240
     */
241
    private function match($pattern, array $request_params, $default = null, $return = 'value')
242
    {
243
        $return = in_array($return, array('bool', 'key', 'value'), true)
244
            ? $return
245
            : 'is_set';
246
        // replace wildcard chars with regex chars
247
        $pattern = str_replace(
248
            array("\*", "\?"),
249
            array('.*', '.'),
250
            preg_quote($pattern, '/')
251
        );
252
        foreach ($request_params as $key => $request_param) {
253
            if (preg_match('/^' . $pattern . '$/is', $key)) {
254
                // return value for request param
255
                if ($return === 'value'){
256
                    return $request_params[ $key ];
257
                }
258
                // or actual key or true just to indicate it was found
259
                return $return === 'key' ? $key : true;
260
            }
261
        }
262
        // match not found so return default value or false
263
        return $return === 'value' ? $default : false;
264
    }
265
266
    /**
267
     * the supplied key can be a simple string to represent a "top-level" request parameter
268
     * or represent a key for a request parameter that is nested deeper within the request parameter array,
269
     * by using square brackets to surround keys for deeper array elements.
270
     * For example :
271
     * if the supplied $key was: "first[second][third]"
272
     * then this will attempt to drill down into the request parameter array to find a value.
273
     * Given the following request parameters:
274
     *  array(
275
     *      'first' => array(
276
     *          'second' => array(
277
     *              'third' => 'has a value'
278
     *          )
279
     *      )
280
     *  )
281
     * would return true if default parameters were set
282
     *
283
     * @param string $callback
284
     * @param        $key
285
     * @param null   $default
286
     * @param array  $request_params
287
     * @return bool|mixed|null
288
     */
289
    private function request_parameter_drill_down(
290
        $key,
291
        $default = null,
292
        $callback = 'is_set',
293
        array $request_params = array()
294
    ) {
295
        $callback = in_array($callback, array('is_set', 'get', 'match'), true)
296
            ? $callback
297
            : 'is_set';
298
        $request_params = ! empty($request_params)
299
            ? $request_params
300
            : $this->_params;
301
        // does incoming key represent an array like 'first[second][third]'  ?
302
        if (strpos($key, '[') !== false) {
303
            // turn it into an actual array
304
            $key  = str_replace(']', '', $key);
305
            $keys = explode('[', $key);
306
            $key  = array_shift($keys);
307
            if ($callback === 'match') {
308
                $real_key = $this->match($key, $request_params, $default, 'key');
309
                $key = $real_key ? $real_key : $key;
310
            }
311
            // check if top level key exists
312
            if (isset($request_params[ $key ])) {
313
                // build a new key to pass along like: 'second[third]'
314
                // or just 'second' depending on depth of keys
315
                $key_string = array_shift($keys);
316
                if (! empty($keys)) {
317
                    $key_string .= '[' . implode('][', $keys) . ']';
318
                }
319
                return $this->request_parameter_drill_down(
320
                    $key_string,
321
                    $default,
322
                    $callback,
323
                    $request_params[ $key ]
324
                );
325
            }
326
        }
327
        if ($callback === 'is_set') {
328
            return isset($request_params[$key]);
329
        }
330
        if ($callback === 'match') {
331
            return $this->match($key, $request_params, $default);
332
        }
333
        return isset($request_params[$key])
334
            ? $request_params[$key]
335
            : $default;
336
    }
337
338
339
340
    /**
341
     * remove param
342
     *
343
     * @param      $key
344
     * @param bool $unset_from_global_too
345
     */
346
    public function un_set($key, $unset_from_global_too = false)
347
    {
348
        unset($this->_params[$key]);
349
        if ($unset_from_global_too) {
350
            unset($_REQUEST[$key]);
351
        }
352
    }
353
354
355
356
    /**
357
     * @return string
358
     */
359
    public function ip_address()
360
    {
361
        return $this->_ip_address;
362
    }
363
364
365
    /**
366
     * @return bool
367
     */
368
    public function isAdmin()
369
    {
370
        return $this->admin;
371
    }
372
373
374
    /**
375
     * @return mixed
376
     */
377
    public function isAjax()
378
    {
379
        return $this->ajax;
380
    }
381
382
383
    /**
384
     * @return mixed
385
     */
386
    public function isFrontAjax()
387
    {
388
        return $this->front_ajax;
389
    }
390
391
392
393
    /**
394
     * _visitor_ip
395
     *    attempt to get IP address of current visitor from server
396
     * plz see: http://stackoverflow.com/a/2031935/1475279
397
     *
398
     * @access public
399
     * @return string
400
     */
401 View Code Duplication
    private function _visitor_ip()
402
    {
403
        $visitor_ip  = '0.0.0.0';
404
        $server_keys = array(
405
            'HTTP_CLIENT_IP',
406
            'HTTP_X_FORWARDED_FOR',
407
            'HTTP_X_FORWARDED',
408
            'HTTP_X_CLUSTER_CLIENT_IP',
409
            'HTTP_FORWARDED_FOR',
410
            'HTTP_FORWARDED',
411
            'REMOTE_ADDR',
412
        );
413
        foreach ($server_keys as $key) {
414
            if (isset($_SERVER[$key])) {
415
                foreach (array_map('trim', explode(',', $_SERVER[$key])) as $ip) {
416
                    if ($ip === '127.0.0.1' || filter_var($ip, FILTER_VALIDATE_IP) !== false) {
417
                        $visitor_ip = $ip;
418
                    }
419
                }
420
            }
421
        }
422
        return $visitor_ip;
423
    }
424
425
426
427
}
428
// End of file EE_Request.core.php
429
// Location: /core/request_stack/EE_Request.core.php
430