Issues (52)

src/Queries/GroupByQuery.php (3 issues)

1
<?php
2
declare(strict_types=1);
3
4
namespace Level23\Druid\Queries;
5
6
use Level23\Druid\Limits\Limit;
7
use Level23\Druid\Types\Granularity;
8
use Level23\Druid\Limits\LimitInterface;
9
use Level23\Druid\Filters\FilterInterface;
10
use Level23\Druid\Context\ContextInterface;
11
use Level23\Druid\Collections\IntervalCollection;
12
use Level23\Druid\Responses\GroupByQueryResponse;
13
use Level23\Druid\Collections\DimensionCollection;
14
use Level23\Druid\DataSources\DataSourceInterface;
15
use Level23\Druid\Aggregations\AggregatorInterface;
16
use Level23\Druid\Collections\AggregationCollection;
17
use Level23\Druid\Collections\VirtualColumnCollection;
18
use Level23\Druid\HavingFilters\HavingFilterInterface;
19
use Level23\Druid\Collections\PostAggregationCollection;
20
use Level23\Druid\PostAggregations\PostAggregatorInterface;
21
22
class GroupByQuery implements QueryInterface
23
{
24
    protected DataSourceInterface $dataSource;
25
26
    protected DimensionCollection $dimensions;
27
28
    protected Granularity $granularity;
29
30
    protected ?FilterInterface $filter = null;
31
32
    protected ?AggregationCollection $aggregations = null;
33
34
    protected ?PostAggregationCollection $postAggregations = null;
35
36
    protected ?VirtualColumnCollection $virtualColumns = null;
37
38
    protected ?HavingFilterInterface $having = null;
39
40
    protected ?ContextInterface $context = null;
41
42
    protected ?Limit $limit = null;
43
44
    protected IntervalCollection $intervals;
45
46
    /**
47
     * @var array<array<string>>
48
     */
49
    protected array $subtotals = [];
50
51
    /**
52
     * GroupByQuery constructor.
53
     *
54
     * @param DataSourceInterface                                   $dataSource
55
     * @param \Level23\Druid\Collections\DimensionCollection        $dimensions
56
     * @param \Level23\Druid\Collections\IntervalCollection         $intervals
57
     * @param AggregationCollection|array<AggregatorInterface>|null $aggregations
58
     * @param string|Granularity                                    $granularity
59
     */
60 6
    public function __construct(
61
        DataSourceInterface $dataSource,
62
        DimensionCollection $dimensions,
63
        IntervalCollection $intervals,
64
        array|AggregationCollection|null $aggregations = null,
65
        string|Granularity $granularity = 'all'
66
    ) {
67 6
        $this->dataSource  = $dataSource;
68 6
        $this->dimensions  = $dimensions;
69 6
        $this->granularity = is_string($granularity) ? Granularity::from(strtolower($granularity)) : $granularity;
70 5
        $this->intervals   = $intervals;
71
72 5
        if ($aggregations) {
73 3
            $this->setAggregations($aggregations);
74
        }
75
    }
76
77
    /**
78
     * Return the query in array format, so we can fire it to druid.
79
     *
80
     * @return array<string,string|array<mixed>>
81
     */
82 1
    public function toArray(): array
83
    {
84 1
        $query = [
85 1
            'queryType'   => 'groupBy',
86 1
            'dataSource'  => $this->dataSource->toArray(),
87 1
            'intervals'   => $this->intervals->toArray(),
88 1
            'dimensions'  => $this->dimensions->toArray(),
89 1
            'granularity' => $this->granularity->value,
90 1
        ];
91
92 1
        if ($this->filter) {
93 1
            $query['filter'] = $this->filter->toArray();
94
        }
95
96 1
        if ($this->aggregations) {
97 1
            $query['aggregations'] = $this->aggregations->toArray();
98
        }
99
100 1
        if ($this->postAggregations) {
101 1
            $query['postAggregations'] = $this->postAggregations->toArray();
102
        }
103
104 1
        if ($this->virtualColumns) {
105 1
            $query['virtualColumns'] = $this->virtualColumns->toArray();
106
        }
107
108 1
        if ($this->having) {
109 1
            $query['having'] = $this->having->toArray();
110
        }
111
112 1
        if (isset($this->context)) {
113 1
            $context = $this->context->toArray();
0 ignored issues
show
The method toArray() does not exist on null. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

113
            /** @scrutinizer ignore-call */ 
114
            $context = $this->context->toArray();

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
114 1
            if (sizeof($context) > 0) {
115 1
                $query['context'] = $context;
116
            }
117
        }
118
119 1
        if ($this->limit) {
120 1
            $query['limitSpec'] = $this->limit->toArray();
121
        }
122
123 1
        if (count($this->subtotals) > 0) {
124 1
            $query['subtotalsSpec'] = $this->subtotals;
125
        }
126
127 1
        return $query;
128
    }
129
130
    /**
131
     * @param \Level23\Druid\Filters\FilterInterface $filter
132
     */
133 1
    public function setFilter(FilterInterface $filter): void
134
    {
135 1
        $this->filter = $filter;
136
    }
137
138
    /**
139
     * @param \Level23\Druid\Collections\AggregationCollection|array<AggregatorInterface> $aggregations
140
     */
141 3
    public function setAggregations(array|AggregationCollection $aggregations): void
142
    {
143 3
        if (is_array($aggregations)) {
0 ignored issues
show
The condition is_array($aggregations) is always true.
Loading history...
144 3
            $aggregations = new AggregationCollection(...$aggregations);
145
        }
146
147 3
        $this->aggregations = $aggregations;
148
    }
149
150
    /**
151
     * @param \Level23\Druid\Collections\PostAggregationCollection|array<PostAggregatorInterface> $postAggregations
152
     */
153 1
    public function setPostAggregations(PostAggregationCollection|array $postAggregations): void
154
    {
155 1
        if (is_array($postAggregations)) {
0 ignored issues
show
The condition is_array($postAggregations) is always true.
Loading history...
156 1
            $postAggregations = new PostAggregationCollection(...$postAggregations);
157
        }
158
159 1
        $this->postAggregations = $postAggregations;
160
    }
161
162
    /**
163
     * @param \Level23\Druid\HavingFilters\HavingFilterInterface $having
164
     */
165 1
    public function setHaving(HavingFilterInterface $having): void
166
    {
167 1
        $this->having = $having;
168
    }
169
170
    /**
171
     * @param \Level23\Druid\Context\ContextInterface $context
172
     */
173 1
    public function setContext(ContextInterface $context): void
174
    {
175 1
        $this->context = $context;
176
    }
177
178
    /**
179
     * @param \Level23\Druid\Limits\Limit|int $limit
180
     */
181 2
    public function setLimit(Limit|int $limit): void
182
    {
183 2
        if ($limit instanceof LimitInterface) {
184 1
            $this->limit = $limit;
185
        } else {
186
187 2
            if (!$this->limit) {
188 1
                $this->limit = new Limit();
189
            }
190
191 2
            $this->limit->setLimit($limit);
192
        }
193
    }
194
195
    /**
196
     * The "offset" parameter tells Druid to skip this many rows when returning results.
197
     *
198
     * @param int $offset
199
     */
200 2
    public function setOffset(int $offset): void
201
    {
202 2
        if (!$this->limit) {
203 1
            $this->limit = new Limit();
204
        }
205 2
        $this->limit->setOffset($offset);
206
    }
207
208
    /**
209
     * Parse the response into something we can return to the user.
210
     *
211
     * @param array<string|int,string|int|array<mixed>> $response
212
     *
213
     * @return GroupByQueryResponse
214
     */
215 1
    public function parseResponse(array $response): GroupByQueryResponse
216
    {
217 1
        return new GroupByQueryResponse($response);
218
    }
219
220
    /**
221
     * @param \Level23\Druid\Collections\VirtualColumnCollection $virtualColumns
222
     */
223 1
    public function setVirtualColumns(VirtualColumnCollection $virtualColumns): void
224
    {
225 1
        $this->virtualColumns = $virtualColumns;
226
    }
227
228
    /**
229
     * @param array<array<string>> $subtotals
230
     */
231 1
    public function setSubtotals(array $subtotals): void
232
    {
233 1
        $this->subtotals = $subtotals;
234
    }
235
}