GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.

Expression::whereElemNotMatch()   A
last analyzed

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
c 0
b 0
f 0
dl 0
loc 4
rs 10
cc 1
eloc 2
nc 1
nop 2
1
<?php
2
3
/**
4
 * This file is part of the PHPMongo package.
5
 *
6
 * (c) Dmytro Sokil <[email protected]>
7
 *
8
 * For the full copyright and license information, please view the LICENSE
9
 * file that was distributed with this source code.
10
 */
11
12
namespace Sokil\Mongo;
13
14
use Sokil\Mongo\Enum\FieldType;
15
use GeoJson\Geometry\Geometry;
16
use GeoJson\Geometry\Point;
17
use Sokil\Mongo\Type\TypeChecker;
18
19
/**
20
 * This class represents all expressions used to query document from collection
21
 *
22
 * @link http://docs.mongodb.org/manual/reference/operator/query/
23
 * @author Dmytro Sokil <[email protected]>
24
 */
25
class Expression implements ArrayableInterface
26
{
27
    /**
28
     * @deprecated Since 1.22 using this property is NOT ALLOWED. Use getters and setters instead.
29
     * @var array
30
     */
31
    protected $_expression = array();
32
33
    /**
34
     * Create new instance of expression
35
     * @return Expression
36
     */
37
    public function expression()
0 ignored issues
show
Coding Style Best Practice introduced by
Please use __construct() instead of a PHP4-style constructor that is named after the class.
Loading history...
38
    {
39
        return new self;
40
    }
41
    /**
42
     * @param string $field
43
     * @param string|array $value
44
     *
45
     * @return Expression
46
     */
47
    public function where($field, $value)
48
    {
49
        if (!isset($this->_expression[$field]) || !is_array($value) || !is_array($this->_expression[$field])) {
0 ignored issues
show
Deprecated Code introduced by
The property Sokil\Mongo\Expression::$_expression has been deprecated with message: Since 1.22 using this property is NOT ALLOWED. Use getters and setters instead.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
50
            $this->_expression[$field] = $value;
0 ignored issues
show
Deprecated Code introduced by
The property Sokil\Mongo\Expression::$_expression has been deprecated with message: Since 1.22 using this property is NOT ALLOWED. Use getters and setters instead.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
51
        } else {
52
            $this->_expression[$field] = array_merge_recursive($this->_expression[$field], $value);
0 ignored issues
show
Deprecated Code introduced by
The property Sokil\Mongo\Expression::$_expression has been deprecated with message: Since 1.22 using this property is NOT ALLOWED. Use getters and setters instead.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
53
        }
54
55
        return $this;
56
    }
57
58
    /**
59
     * Filter empty field
60
     *
61
     * @param string $field
62
     *
63
     * @return Expression
64
     */
65 View Code Duplication
    public function whereEmpty($field)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
66
    {
67
        return $this->where(
68
            '$or',
69
            array(
70
                array($field => null),
71
                array($field => ''),
72
                array($field => array()),
73
                array($field => array('$exists' => false))
74
            )
75
        );
76
    }
77
78 View Code Duplication
    public function whereNotEmpty($field)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
79
    {
80
        return $this->where('$nor', array(
81
            array($field => null),
82
            array($field => ''),
83
            array($field => array()),
84
            array($field => array('$exists' => false))
85
        ));
86
    }
87
88
    public function whereGreater($field, $value)
89
    {
90
        return $this->where($field, array('$gt' => $value));
91
    }
92
93
    public function whereGreaterOrEqual($field, $value)
94
    {
95
        return $this->where($field, array('$gte' => $value));
96
    }
97
98
    public function whereLess($field, $value)
99
    {
100
        return $this->where($field, array('$lt' => $value));
101
    }
102
103
    public function whereLessOrEqual($field, $value)
104
    {
105
        return $this->where($field, array('$lte' => $value));
106
    }
107
108
    public function whereNotEqual($field, $value)
109
    {
110
        return $this->where($field, array('$ne' => $value));
111
    }
112
113
    /**
114
     * Selects the documents where the value of a
115
     * field equals any value in the specified array.
116
     *
117
     * @param string $field
118
     * @param array $values
119
     * @return Expression
120
     */
121
    public function whereIn($field, array $values)
122
    {
123
        return $this->where($field, array('$in' => $values));
124
    }
125
126
    public function whereNotIn($field, array $values)
127
    {
128
        return $this->where($field, array('$nin' => $values));
129
    }
130
131
    public function whereExists($field)
132
    {
133
        return $this->where($field, array('$exists' => true));
134
    }
135
136
    public function whereNotExists($field)
137
    {
138
        return $this->where($field, array('$exists' => false));
139
    }
140
141
    public function whereHasType($field, $type)
142
    {
143
        return $this->where($field, array('$type' => (int) $type));
144
    }
145
146
    public function whereDouble($field)
147
    {
148
        return $this->whereHasType($field, FieldType::DOUBLE);
149
    }
150
151
    public function whereString($field)
152
    {
153
        return $this->whereHasType($field, FieldType::STRING);
154
    }
155
156
    public function whereObject($field)
157
    {
158
        return $this->whereHasType($field, FieldType::OBJECT);
159
    }
160
161
    public function whereBoolean($field)
162
    {
163
        return $this->whereHasType($field, FieldType::BOOLEAN);
164
    }
165
166
    public function whereArray($field)
167
    {
168
        return $this->whereJsCondition('Array.isArray(this.' . $field . ')');
169
    }
170
171
    public function whereArrayOfArrays($field)
172
    {
173
        return $this->whereHasType($field, FieldType::ARRAY_TYPE);
174
    }
175
176
    public function whereObjectId($field)
177
    {
178
        return $this->whereHasType($field, FieldType::OBJECT_ID);
179
    }
180
181
    public function whereDate($field)
182
    {
183
        return $this->whereHasType($field, FieldType::DATE);
184
    }
185
186
    public function whereNull($field)
187
    {
188
        return $this->whereHasType($field, FieldType::NULL);
189
    }
190
191
    public function whereJsCondition($condition)
192
    {
193
        return $this->where('$where', $condition);
194
    }
195
196
    public function whereLike($field, $regex, $caseInsensitive = true)
197
    {
198
        // regex
199
        $expression = array(
200
            '$regex'    => $regex,
201
        );
202
203
        // options
204
        $options = '';
205
206
        if ($caseInsensitive) {
207
            $options .= 'i';
208
        }
209
210
        $expression['$options'] = $options;
211
212
        // query
213
        return $this->where($field, $expression);
214
    }
215
216
    /**
217
     * Find documents where the value of a field is an array
218
     * that contains all the specified elements.
219
     * This is equivalent of logical AND.
220
     *
221
     * @link http://docs.mongodb.org/manual/reference/operator/query/all/
222
     *
223
     * @param string $field point-delimited field name
224
     * @param array $values
225
     * @return Expression
226
     */
227
    public function whereAll($field, array $values)
228
    {
229
        return $this->where($field, array('$all' => $values));
230
    }
231
232
    /**
233
     * Find documents where the value of a field is an array
234
     * that contains none of the specified elements.
235
     * This is equivalent of logical AND.
236
     *
237
     * @link http://docs.mongodb.org/manual/reference/operator/query/all/
238
     *
239
     * @param string $field point-delimited field name
240
     * @param array $values
241
     * @return Expression
242
     */
243
    public function whereNoneOf($field, array $values)
244
    {
245
        return $this->where($field, array(
246
            '$not' => array(
247
                '$all' => $values
248
            ),
249
        ));
250
    }
251
252
    /**
253
     * Find documents where the value of a field is an array
254
     * that contains any of the specified elements.
255
     * This is equivalent of logical AND.
256
     *
257
     * @param string $field point-delimited field name
258
     * @param array $values
259
     * @return Expression
260
     */
261
    public function whereAny($field, array $values)
262
    {
263
        return $this->whereIn($field, $values);
264
    }
265
266
    /**
267
     * Matches documents in a collection that contain an array field with at
268
     * least one element that matches all the specified query criteria.
269
     *
270
     * @param string $field point-delimited field name
271
     * @param \Sokil\Mongo\Expression|callable|array $expression
272
     *
273
     * @return Expression
274
     *
275
     * @throws Exception
276
     */
277
    public function whereElemMatch($field, $expression)
278
    {
279
        if (is_callable($expression)) {
280
            $expression = call_user_func($expression, $this->expression());
281
        }
282
283 View Code Duplication
        if ($expression instanceof Expression) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
284
            $expression = $expression->toArray();
285
        } elseif (!is_array($expression)) {
286
            throw new Exception('Wrong expression passed');
287
        }
288
289
        return $this->where($field, array('$elemMatch' => $expression));
290
    }
291
292
    /**
293
     * Matches documents in a collection that contain an array field with elements
294
     * that do not matches all the specified query criteria.
295
     *
296
     * @param string $field
297
     * @param Expression|callable|array $expression
298
     *
299
     * @return Expression
300
     */
301
    public function whereElemNotMatch($field, $expression)
302
    {
303
        return $this->whereNot($this->expression()->whereElemMatch($field, $expression));
304
    }
305
306
    /**
307
     * Selects documents if the array field is a specified size.
308
     *
309
     * @param string $field
310
     * @param integer $length
311
     * @return Expression
312
     */
313
    public function whereArraySize($field, $length)
314
    {
315
        return $this->where($field, array('$size' => (int) $length));
316
    }
317
318
    /**
319
     * Selects the documents that satisfy at least one of the expressions
320
     *
321
     * @param array|\Sokil\Mongo\Expression $expressions Array of Expression instances or comma delimited expression list
322
     *
323
     * @return Expression
324
     */
325 View Code Duplication
    public function whereOr($expressions = null /**, ...**/)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
326
    {
327
        if ($expressions instanceof Expression) {
328
            $expressions = func_get_args();
329
        }
330
331
        return $this->where('$or', array_map(function (Expression $expression) {
332
            return $expression->toArray();
333
        }, $expressions));
334
    }
335
336
    /**
337
     * Select the documents that satisfy all the expressions in the array
338
     *
339
     * @param array|\Sokil\Mongo\Expression $expressions Array of Expression instances or comma delimited expression list
340
     * @return Expression
341
     */
342 View Code Duplication
    public function whereAnd($expressions = null /**, ...**/)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
343
    {
344
        if ($expressions instanceof Expression) {
345
            $expressions = func_get_args();
346
        }
347
348
        return $this->where('$and', array_map(function (Expression $expression) {
349
            return $expression->toArray();
350
        }, $expressions));
351
    }
352
353
    /**
354
     * Selects the documents that fail all the query expressions in the array
355
     *
356
     * @param array|\Sokil\Mongo\Expression $expressions Array of Expression instances or comma delimited expression list
357
     * @return Expression
358
     */
359 View Code Duplication
    public function whereNor($expressions = null /**, ...**/)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
360
    {
361
        if ($expressions instanceof Expression) {
362
            $expressions = func_get_args();
363
        }
364
365
        return $this->where(
366
            '$nor',
367
            array_map(
368
                function (Expression $expression) {
369
                    return $expression->toArray();
370
                },
371
                $expressions
372
            )
373
        );
374
    }
375
376
    public function whereNot(Expression $expression)
377
    {
378
        foreach ($expression->toArray() as $field => $value) {
379
            if (TypeChecker::isExpression($value) || TypeChecker::isRegex($value)) {
380
                // $not acceptable only for operators-expressions or regexps
381
                $this->where($field, array('$not' => $value));
382
            } else {
383
                // for single values use $ne
384
                $this->whereNotEqual($field, $value);
385
            }
386
        }
387
388
        return $this;
389
    }
390
391
    /**
392
     * Select documents where the value of a field divided by a divisor has the specified remainder (i.e. perform a modulo operation to select documents)
393
     *
394
     * @param string $field
395
     * @param int $divisor
396
     * @param int $remainder
397
     */
398
    public function whereMod($field, $divisor, $remainder)
399
    {
400
        $this->where($field, array(
401
            '$mod' => array((int) $divisor, (int) $remainder),
402
        ));
403
404
        return $this;
405
    }
406
407
    /**
408
     * Perform fulltext search
409
     *
410
     * @link https://docs.mongodb.org/manual/reference/operator/query/text/
411
     * @link https://docs.mongodb.org/manual/tutorial/specify-language-for-text-index/
412
     *
413
     * If a collection contains documents or embedded documents that are in different languages,
414
     * include a field named language in the documents or embedded documents and specify as its value the language
415
     * for that document or embedded document.
416
     *
417
     * The specified language in the document overrides the default language for the text index.
418
     * The specified language in an embedded document override the language specified in an enclosing document or
419
     * the default language for the index.
420
     *
421
     * Case Insensitivity:
422
     * @link https://docs.mongodb.org/manual/reference/operator/query/text/#text-operator-case-sensitivity
423
     *
424
     * Diacritic Insensitivity:
425
     * @link https://docs.mongodb.org/manual/reference/operator/query/text/#text-operator-diacritic-sensitivity
426
     *
427
     * @param $search A string of terms that MongoDB parses and uses to query the text index. MongoDB performs a
428
     *  logical OR search of the terms unless specified as a phrase.
429
     * @param $language Optional. The language that determines the list of stop words for the search and the
430
     *  rules for the stemmer and tokenizer. If not specified, the search uses the default language of the index.
431
     *  If you specify a language value of "none", then the text search uses simple tokenization
432
     *  with no list of stop words and no stemming.
433
     * @param bool|false $caseSensitive Allowed from v.3.2 A boolean flag to enable or disable case
434
     *  sensitive search. Defaults to false; i.e. the search defers to the case insensitivity of the text index.
435
     * @param bool|false $diacriticSensitive Allowed from v.3.2 A boolean flag to enable or disable diacritic
436
     *  sensitive search against version 3 text indexes. Defaults to false; i.e. the search defers to the diacritic
437
     *  insensitivity of the text index. Text searches against earlier versions of the text index are inherently
438
     *  diacritic sensitive and cannot be diacritic insensitive. As such, the $diacriticSensitive option has no
439
     *  effect with earlier versions of the text index.
440
     * @return $this
441
     */
442
    public function whereText(
443
        $search,
444
        $language = null,
445
        $caseSensitive = null,
446
        $diacriticSensitive = null
447
    ) {
448
        $this->_expression['$text'] = array(
0 ignored issues
show
Deprecated Code introduced by
The property Sokil\Mongo\Expression::$_expression has been deprecated with message: Since 1.22 using this property is NOT ALLOWED. Use getters and setters instead.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
449
            '$search' => $search,
450
        );
451
452
        if ($language) {
453
            $this->_expression['$text']['$language'] = $language;
0 ignored issues
show
Deprecated Code introduced by
The property Sokil\Mongo\Expression::$_expression has been deprecated with message: Since 1.22 using this property is NOT ALLOWED. Use getters and setters instead.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
454
        }
455
456
        // Version 3.2 feature
457
        if ($caseSensitive) {
458
            $this->_expression['$text']['$caseSensitive'] = (bool) $caseSensitive;
0 ignored issues
show
Deprecated Code introduced by
The property Sokil\Mongo\Expression::$_expression has been deprecated with message: Since 1.22 using this property is NOT ALLOWED. Use getters and setters instead.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
459
        }
460
461
        // Version 3.2 feature
462
        if ($diacriticSensitive) {
463
            $this->_expression['$text']['$diacriticSensitive'] = (bool) $diacriticSensitive;
0 ignored issues
show
Deprecated Code introduced by
The property Sokil\Mongo\Expression::$_expression has been deprecated with message: Since 1.22 using this property is NOT ALLOWED. Use getters and setters instead.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
464
        }
465
466
        return $this;
467
    }
468
469
    /**
470
     * Find document near points in flat surface
471
     *
472
     * @param string $field
473
     * @param float $longitude
474
     * @param float $latitude
475
     * @param int|array $distance distance from point in meters. Array distance
476
     *  allowed only in MongoDB 2.6
477
     * @return Expression
478
     */
479 View Code Duplication
    public function nearPoint($field, $longitude, $latitude, $distance)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
480
    {
481
        $point = new \GeoJson\Geometry\Point(array(
482
            (float) $longitude,
483
            (float) $latitude
484
        ));
485
486
        $near = array(
487
            '$geometry' => $point->jsonSerialize(),
488
        );
489
490
        if (is_array($distance)) {
491
            if (!empty($distance[0])) {
492
                $near['$minDistance'] = (int) $distance[0];
493
            }
494
            if (!empty($distance[1])) {
495
                $near['$maxDistance'] = (int) $distance[1];
496
            }
497
        } else {
498
            $near['$maxDistance'] = (int) $distance;
499
        }
500
501
        $this->where($field, array('$near' => $near));
502
503
        return $this;
504
    }
505
506
    /**
507
     * Find document near points in spherical surface
508
     *
509
     * @param string $field
510
     * @param float $longitude
511
     * @param float $latitude
512
     * @param int|array $distance distance from point in meters. Array distance
513
     *  allowed only in MongoDB 2.6
514
     * @return Expression
515
     */
516 View Code Duplication
    public function nearPointSpherical($field, $longitude, $latitude, $distance)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
517
    {
518
        $point = new Point(array(
519
            (float) $longitude,
520
            (float) $latitude
521
        ));
522
523
        $near = array(
524
            '$geometry' => $point->jsonSerialize(),
525
        );
526
527
        if (is_array($distance)) {
528
            if (!empty($distance[0])) {
529
                $near['$minDistance'] = (int) $distance[0];
530
            }
531
            if (!empty($distance[1])) {
532
                $near['$maxDistance'] = (int) $distance[1];
533
            }
534
        } else {
535
            $near['$maxDistance'] = (int) $distance;
536
        }
537
538
        $this->where($field, array('$nearSphere' => $near));
539
540
        return $this;
541
    }
542
543
    /**
544
     * Selects documents whose geospatial data intersects with a specified
545
     * GeoJSON object; i.e. where the intersection of the data and the
546
     * specified object is non-empty. This includes cases where the data
547
     * and the specified object share an edge. Uses spherical geometry.
548
     *
549
     * @link http://docs.mongodb.org/manual/reference/operator/query/geoIntersects/
550
     *
551
     * @param string $field
552
     * @param Geometry $geometry
553
     * @return Expression
554
     */
555
    public function intersects($field, Geometry $geometry)
556
    {
557
        $this->where($field, array(
558
            '$geoIntersects' => array(
559
                '$geometry' => $geometry->jsonSerialize(),
560
            ),
561
        ));
562
563
        return $this;
564
    }
565
566
    /**
567
     * Selects documents with geospatial data that exists entirely within a specified shape.
568
     *
569
     * @link http://docs.mongodb.org/manual/reference/operator/query/geoWithin/
570
     * @param string $field
571
     * @param Geometry $geometry
572
     * @return Expression
573
     */
574
    public function within($field, Geometry $geometry)
575
    {
576
        $this->where($field, array(
577
            '$geoWithin' => array(
578
                '$geometry' => $geometry->jsonSerialize(),
579
            ),
580
        ));
581
582
        return $this;
583
    }
584
585
    /**
586
     * Select documents with geospatial data within circle defined
587
     * by center point and radius in flat surface
588
     *
589
     * @param string $field
590
     * @param float $longitude
591
     * @param float $latitude
592
     * @param float $radius
593
     * @return Expression
594
     */
595
    public function withinCircle($field, $longitude, $latitude, $radius)
596
    {
597
        $this->where($field, array(
598
            '$geoWithin' => array(
599
                '$center' => array(
600
                    array($longitude, $latitude),
601
                    $radius,
602
                ),
603
            ),
604
        ));
605
606
        return $this;
607
    }
608
609
    /**
610
     * Select documents with geospatial data within circle defined
611
     * by center point and radius in spherical surface
612
     *
613
     * To calculate distance in radians
614
     * @see http://docs.mongodb.org/manual/tutorial/calculate-distances-using-spherical-geometry-with-2d-geospatial-indexes/
615
     *
616
     * @param string $field
617
     * @param float $longitude
618
     * @param float $latitude
619
     * @param float $radiusInRadians in radians.
620
     * @return Expression
621
     */
622
    public function withinCircleSpherical($field, $longitude, $latitude, $radiusInRadians)
623
    {
624
        $this->where($field, array(
625
            '$geoWithin' => array(
626
                '$centerSphere' => array(
627
                    array($longitude, $latitude),
628
                    $radiusInRadians,
629
                ),
630
            ),
631
        ));
632
633
        return $this;
634
    }
635
636
    /**
637
     * Return documents that are within the bounds of the rectangle, according
638
     * to their point-based location data.
639
     *
640
     * Based on grid coordinates and does not query for GeoJSON shapes.
641
     *
642
     * Use planar geometry, so 2d index may be used but not required
643
     *
644
     * @param string $field
645
     * @param array $bottomLeftCoordinate Bottom left coordinate of box
646
     * @param array $upperRightCoordinate Upper right coordinate of box
647
     * @return Expression
648
     */
649
    public function withinBox($field, array $bottomLeftCoordinate, array $upperRightCoordinate)
650
    {
651
        $this->where($field, array(
652
            '$geoWithin' => array(
653
                '$box' => array(
654
                    $bottomLeftCoordinate,
655
                    $upperRightCoordinate,
656
                ),
657
            ),
658
        ));
659
660
        return $this;
661
    }
662
663
    /**
664
     * Return documents that are within the polygon, according
665
     * to their point-based location data.
666
     *
667
     * Based on grid coordinates and does not query for GeoJSON shapes.
668
     *
669
     * Use planar geometry, so 2d index may be used but not required
670
     *
671
     * @param string $field
672
     * @param array $points array of coordinates
673
     * @return Expression
674
     */
675
    public function withinPolygon($field, array $points)
676
    {
677
        $this->where($field, array(
678
            '$geoWithin' => array(
679
                '$polygon' => $points,
680
            ),
681
        ));
682
683
        return $this;
684
    }
685
686
    public function toArray()
687
    {
688
        return $this->_expression;
0 ignored issues
show
Deprecated Code introduced by
The property Sokil\Mongo\Expression::$_expression has been deprecated with message: Since 1.22 using this property is NOT ALLOWED. Use getters and setters instead.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
689
    }
690
691
    public function merge(Expression $expression)
692
    {
693
        $this->_expression = array_merge_recursive($this->_expression, $expression->toArray());
0 ignored issues
show
Deprecated Code introduced by
The property Sokil\Mongo\Expression::$_expression has been deprecated with message: Since 1.22 using this property is NOT ALLOWED. Use getters and setters instead.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
694
        return $this;
695
    }
696
697
    /**
698
     * Transform expression in different formats to canonical array form
699
     *
700
     * @param callable|array|Expression $mixed
701
     *
702
     * @return array
703
     *
704
     * @throws \Sokil\Mongo\Exception
705
     */
706
    public static function convertToArray($mixed)
707
    {
708
        // get expression from callable
709
        if (is_callable($mixed)) {
710
            $callable = $mixed;
711
            $mixed = new self();
712
            call_user_func($callable, $mixed);
713
        }
714
715
        // get expression array
716
        if ($mixed instanceof ArrayableInterface && $mixed instanceof self) {
717
            $mixed = $mixed->toArray();
718
        } elseif (!is_array($mixed)) {
719
            throw new Exception(sprintf(
720
                'Mixed must be instance of "\Sokil\Mongo\Expression", array or callable that accepts "\Sokil\Mongo\Expression", "%s" given',
721
                gettype($mixed) === "object" ? get_class($mixed) : gettype($mixed)
722
            ));
723
        }
724
725
        return $mixed;
726
    }
727
}
728