1<?php
2
3namespace Elastica\QueryBuilder\DSL;
4
5use Elastica\Exception\NotImplementedException;
6use Elastica\Query\AbstractQuery;
7use Elastica\Query\AbstractSpanQuery;
8use Elastica\Query as BaseQuery;
9use Elastica\Query\BoolQuery;
10use Elastica\Query\Boosting;
11use Elastica\Query\Common;
12use Elastica\Query\ConstantScore;
13use Elastica\Query\DisMax;
14use Elastica\Query\Exists;
15use Elastica\Query\FunctionScore;
16use Elastica\Query\Fuzzy;
17use Elastica\Query\GeoDistance;
18use Elastica\Query\HasChild;
19use Elastica\Query\HasParent;
20use Elastica\Query\Ids;
21use Elastica\Query\Match;
22use Elastica\Query\MatchAll;
23use Elastica\Query\MatchNone;
24use Elastica\Query\MoreLikeThis;
25use Elastica\Query\MultiMatch;
26use Elastica\Query\Nested;
27use Elastica\Query\ParentId;
28use Elastica\Query\Percolate;
29use Elastica\Query\Prefix;
30use Elastica\Query\QueryString;
31use Elastica\Query\Range;
32use Elastica\Query\Regexp;
33use Elastica\Query\SimpleQueryString;
34use Elastica\Query\SpanContaining;
35use Elastica\Query\SpanFirst;
36use Elastica\Query\SpanMulti;
37use Elastica\Query\SpanNear;
38use Elastica\Query\SpanNot;
39use Elastica\Query\SpanOr;
40use Elastica\Query\SpanTerm;
41use Elastica\Query\SpanWithin;
42use Elastica\Query\Term;
43use Elastica\Query\Terms;
44use Elastica\Query\Type;
45use Elastica\Query\Wildcard;
46use Elastica\QueryBuilder\DSL;
47
48/**
49 * elasticsearch query DSL.
50 *
51 * @author Manuel Andreo Garcia <andreo.garcia@googlemail.com>
52 *
53 * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-queries.html
54 */
55class Query implements DSL
56{
57    /**
58     * must return type for QueryBuilder usage.
59     *
60     * @return string
61     */
62    public function getType(): string
63    {
64        return self::TYPE_QUERY;
65    }
66
67    /**
68     * match query.
69     *
70     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-match-query.html
71     *
72     * @param string $field
73     * @param mixed  $values
74     *
75     * @return Match
76     */
77    public function match(string $field = null, $values = null): Match
78    {
79        return new Match($field, $values);
80    }
81
82    /**
83     * multi match query.
84     *
85     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-multi-match-query.html
86     *
87     * @return MultiMatch
88     */
89    public function multi_match(): MultiMatch
90    {
91        return new MultiMatch();
92    }
93
94    /**
95     * bool query.
96     *
97     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-bool-query.html
98     *
99     * @return BoolQuery
100     */
101    public function bool(): BoolQuery
102    {
103        return new BoolQuery();
104    }
105
106    /**
107     * boosting query.
108     *
109     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-boosting-query.html
110     *
111     * @return Boosting
112     */
113    public function boosting(): Boosting
114    {
115        return new Boosting();
116    }
117
118    /**
119     * common terms query.
120     *
121     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-common-terms-query.html
122     *
123     * @param string $field
124     * @param string $query
125     * @param float  $cutoffFrequency percentage in decimal form (.001 == 0.1%)
126     *
127     * @return Common
128     */
129    public function common_terms(string $field, string $query, float $cutoffFrequency): Common
130    {
131        return new Common($field, $query, $cutoffFrequency);
132    }
133
134    /**
135     * constant score query.
136     *
137     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-constant-score-query.html
138     *
139     * @param AbstractQuery|null $filter
140     *
141     * @return ConstantScore
142     */
143    public function constant_score(AbstractQuery $filter = null): ConstantScore
144    {
145        return new ConstantScore($filter);
146    }
147
148    /**
149     * dis max query.
150     *
151     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-dis-max-query.html
152     *
153     * @return DisMax
154     */
155    public function dis_max(): DisMax
156    {
157        return new DisMax();
158    }
159
160    /**
161     * function score query.
162     *
163     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-function-score-query.html
164     *
165     * @return FunctionScore
166     */
167    public function function_score(): FunctionScore
168    {
169        return new FunctionScore();
170    }
171
172    /**
173     * fuzzy query.
174     *
175     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-fuzzy-query.html
176     *
177     * @param string $fieldName Field name
178     * @param string $value     String to search for
179     *
180     * @return Fuzzy
181     */
182    public function fuzzy(string $fieldName = null, string $value = null): Fuzzy
183    {
184        return new Fuzzy($fieldName, $value);
185    }
186
187    /**
188     * geo shape query.
189     *
190     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-geo-shape-query.html
191     */
192    public function geo_shape()
193    {
194        throw new NotImplementedException();
195    }
196
197    /**
198     * has child query.
199     *
200     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-has-child-query.html
201     *
202     * @param string|BaseQuery|AbstractQuery $query
203     * @param string                         $type  Parent document type
204     *
205     * @return HasChild
206     */
207    public function has_child($query, string $type = null): HasChild
208    {
209        return new HasChild($query, $type);
210    }
211
212    /**
213     * has parent query.
214     *
215     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-has-parent-query.html
216     *
217     * @param string|BaseQuery|AbstractQuery $query
218     * @param string                         $type  Parent document type
219     *
220     * @return HasParent
221     */
222    public function has_parent($query, string $type): HasParent
223    {
224        return new HasParent($query, $type);
225    }
226
227    /**
228     * ids query.
229     *
230     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-ids-query.html
231     *
232     * @param array $ids
233     *
234     * @return Ids
235     */
236    public function ids(array $ids = []): Ids
237    {
238        return new Ids($ids);
239    }
240
241    /**
242     * match all query.
243     *
244     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-match-all-query.html
245     *
246     * @return MatchAll
247     */
248    public function match_all(): MatchAll
249    {
250        return new MatchAll();
251    }
252
253    /**
254     * match none query.
255     *
256     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-match-all-query.html#query-dsl-match-none-query
257     *
258     * @return MatchNone
259     */
260    public function match_none(): MatchNone
261    {
262        return new MatchNone();
263    }
264
265    /**
266     * more like this query.
267     *
268     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-mlt-query.html
269     *
270     * @return MoreLikeThis
271     */
272    public function more_like_this(): MoreLikeThis
273    {
274        return new MoreLikeThis();
275    }
276
277    /**
278     * nested query.
279     *
280     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-nested-query.html
281     *
282     * @return Nested
283     */
284    public function nested(): Nested
285    {
286        return new Nested();
287    }
288
289    /**
290     * @param string     $type
291     * @param int|string $id
292     * @param bool       $ignoreUnmapped
293     *
294     * @return ParentId ParentId
295     */
296    public function parent_id(string $type, $id, bool $ignoreUnmapped = false): ParentId
297    {
298        return new ParentId($type, $id, $ignoreUnmapped);
299    }
300
301    /**
302     * prefix query.
303     *
304     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-prefix-query.html
305     *
306     * @param array $prefix Prefix array
307     *
308     * @return Prefix
309     */
310    public function prefix(array $prefix = []): Prefix
311    {
312        return new Prefix($prefix);
313    }
314
315    /**
316     * query string query.
317     *
318     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-query-string-query.html
319     *
320     * @param string $queryString OPTIONAL Query string for object
321     *
322     * @return QueryString
323     */
324    public function query_string(string $queryString = ''): QueryString
325    {
326        return new QueryString($queryString);
327    }
328
329    /**
330     * simple_query_string query.
331     *
332     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-simple-query-string-query.html
333     *
334     * @param string $query
335     * @param array  $fields
336     *
337     * @return SimpleQueryString
338     */
339    public function simple_query_string(string $query, array $fields = []): SimpleQueryString
340    {
341        return new SimpleQueryString($query, $fields);
342    }
343
344    /**
345     * range query.
346     *
347     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-range-query.html
348     *
349     * @param string $fieldName
350     * @param array  $args
351     *
352     * @return Range
353     */
354    public function range(string $fieldName = null, array $args = []): Range
355    {
356        return new Range($fieldName, $args);
357    }
358
359    /**
360     * regexp query.
361     *
362     * @param string $key
363     * @param string $value
364     * @param float  $boost
365     *
366     * @return Regexp
367     *
368     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-regexp-query.html
369     */
370    public function regexp(string $key = '', string $value = null, float $boost = 1.0): Regexp
371    {
372        return new Regexp($key, $value, $boost);
373    }
374
375    /**
376     * span first query.
377     *
378     * @param AbstractQuery|array $match
379     * @param int                 $end
380     *
381     * @return SpanFirst
382     *
383     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-span-first-query.html
384     */
385    public function span_first($match = null, int $end = null): SpanFirst
386    {
387        return new SpanFirst($match, $end);
388    }
389
390    /**
391     * span multi term query.
392     *
393     * @param AbstractQuery|array $match
394     *
395     * @return SpanMulti
396     *
397     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-span-multi-term-query.html
398     */
399    public function span_multi_term($match = null): SpanMulti
400    {
401        return new SpanMulti($match);
402    }
403
404    /**
405     * span near query.
406     *
407     * @param array $clauses
408     * @param int   $slop
409     * @param bool  $inOrder
410     *
411     * @return SpanNear
412     *
413     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-span-near-query.html
414     */
415    public function span_near(array $clauses = [], int $slop = 1, bool $inOrder = false): SpanNear
416    {
417        return new SpanNear($clauses, $slop, $inOrder);
418    }
419
420    /**
421     * span not query.
422     *
423     * @param AbstractSpanQuery|null $include
424     * @param AbstractSpanQuery|null $exclude
425     *
426     * @return SpanNot
427     *
428     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-span-not-query.html
429     */
430    public function span_not(AbstractSpanQuery $include = null, AbstractSpanQuery $exclude = null): SpanNot
431    {
432        return new SpanNot($include, $exclude);
433    }
434
435    /**
436     * span_or query.
437     *
438     * @param array $clauses
439     *
440     * @return SpanOr
441     *
442     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-span-or-query.html
443     */
444    public function span_or(array $clauses = []): SpanOr
445    {
446        return new SpanOr($clauses);
447    }
448
449    /**
450     * span_term query.
451     *
452     * @param array $term
453     *
454     * @return SpanTerm
455     *
456     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-span-term-query.html
457     */
458    public function span_term(array $term = []): SpanTerm
459    {
460        return new SpanTerm($term);
461    }
462
463    /**
464     * span_containing query.
465     *
466     * @param AbstractSpanQuery|null $little
467     * @param AbstractSpanQuery|null $big
468     *
469     * @return SpanContaining
470     *
471     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-span-containing-query.html
472     */
473    public function span_containing(AbstractSpanQuery $little = null, AbstractSpanQuery $big = null): SpanContaining
474    {
475        return new SpanContaining($little, $big);
476    }
477
478    /**
479     * span_within query.
480     *
481     * @param AbstractSpanQuery|null $little
482     * @param AbstractSpanQuery|null $big
483     *
484     * @return SpanWithin
485     *
486     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-span-within-query.html
487     */
488    public function span_within(AbstractSpanQuery $little = null, AbstractSpanQuery $big = null): SpanWithin
489    {
490        return new SpanWithin($little, $big);
491    }
492
493    /**
494     * term query.
495     *
496     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-term-query.html
497     *
498     * @param array $term
499     *
500     * @return Term
501     */
502    public function term(array $term = []): Term
503    {
504        return new Term($term);
505    }
506
507    /**
508     * terms query.
509     *
510     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-terms-query.html
511     *
512     * @param string $key
513     * @param array  $terms
514     *
515     * @return Terms
516     */
517    public function terms(string $key = '', array $terms = []): Terms
518    {
519        return new Terms($key, $terms);
520    }
521
522    /**
523     * wildcard query.
524     *
525     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-wildcard-query.html
526     *
527     * @param string $key   OPTIONAL Wildcard key
528     * @param string $value OPTIONAL Wildcard value
529     * @param float  $boost OPTIONAL Boost value (default = 1)
530     *
531     * @return Wildcard
532     */
533    public function wildcard(string $key = '', string $value = null, float $boost = 1.0): Wildcard
534    {
535        return new Wildcard($key, $value, $boost);
536    }
537
538    /**
539     * geo distance query.
540     *
541     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-geo-distance-query.html
542     *
543     * @param string       $key
544     * @param array|string $location
545     * @param string       $distance
546     *
547     * @return GeoDistance
548     */
549    public function geo_distance(string $key, $location, string $distance): GeoDistance
550    {
551        return new GeoDistance($key, $location, $distance);
552    }
553
554    /**
555     * exists query.
556     *
557     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-exists-query.html
558     *
559     * @param string $field
560     *
561     * @return Exists
562     */
563    public function exists(string $field): Exists
564    {
565        return new Exists($field);
566    }
567
568    /**
569     * type query.
570     *
571     * @see https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-type-query.html
572     *
573     * @param string $type Type name
574     *
575     * @return Type
576     */
577    public function type(string $type = null): Type
578    {
579        return new Type($type);
580    }
581
582    /**
583     * type query.
584     *
585     * @see https://www.elastic.co/guide/en/elasticsearch/reference/5.0/query-dsl-percolate-query.html
586     *
587     * @return Percolate
588     */
589    public function percolate(): Percolate
590    {
591        return new Percolate();
592    }
593}
594