Test Failed
Push — master ( 1c5165...b7ef6a )
by Kirill
03:37
created

ExecutionsProvider::get()   A

Complexity

Conditions 5
Paths 2

Size

Total Lines 20

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 9
CRAP Score 5.1502

Importance

Changes 0
Metric Value
dl 0
loc 20
ccs 9
cts 11
cp 0.8182
rs 9.2888
c 0
b 0
f 0
cc 5
nc 2
nop 1
crap 5.1502
1
<?php
2
/**
3
 * This file is part of Hydrogen package.
4
 *
5
 * For the full copyright and license information, please view the LICENSE
6
 * file that was distributed with this source code.
7
 */
8
declare(strict_types=1);
9
10
namespace RDS\Hydrogen\Query;
11
12
use Illuminate\Support\Arr;
13
use RDS\Hydrogen\Query;
14
use RDS\Hydrogen\Collection\Collection;
15
16
/**
17
 * Class ExecutionsProvider
18
 * @mixin Query
19
 */
20
trait ExecutionsProvider
21
{
22
    /**
23
     * @param string ...$fields
24
     * @return object[]|iterable
25
     */
26 20
    public function get(string ...$fields): iterable
27
    {
28 20
        $processor = $this->getRepository()->getProcessor();
0 ignored issues
show
Bug introduced by
It seems like getRepository() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
29
30 20
        if (\count($fields)) {
31 2
            return \collect($processor->getArrayResult($this))->map(function (array $data) use ($fields) {
32 2
                if (isset($data[0]) && \is_array($data[0])) {
33
                    $data = $data[0];
34
                }
35
36 2
                if (\count($fields)) {
37 2
                    return Arr::only($data, $fields);
38
                }
39
40
                return $data;
41 2
            });
42
        }
43
44 20
        return $processor->getResult($this);
45
    }
46
47
    /**
48
     * Get the values of a given key.
49
     *
50
     * @param string|array $value
51
     * @param string|null $key
52
     * @return Collection|iterable
53
     */
54
    public function pluck($value, $key = null): Collection
55
    {
56
        return $this
0 ignored issues
show
Documentation Bug introduced by
The method pluck does not exist on object<RDS\Hydrogen\Collection\Collection>? Since you implemented __call, maybe consider adding a @method annotation.

If you implement __call and you know which methods are available, you can improve IDE auto-completion and static analysis by adding a @method annotation to the class.

This is often the case, when __call is implemented by a parent class and only the child class knows which methods exist:

class ParentClass {
    private $data = array();

    public function __call($method, array $args) {
        if (0 === strpos($method, 'get')) {
            return $this->data[strtolower(substr($method, 3))];
        }

        throw new \LogicException(sprintf('Unsupported method: %s', $method));
    }
}

/**
 * If this class knows which fields exist, you can specify the methods here:
 *
 * @method string getName()
 */
class SomeClass extends ParentClass { }
Loading history...
57
            ->collect(...\array_filter([$value, $key]))
58
            ->pluck($value, $key);
59
    }
60
61
    /**
62
     * @param string $field
63
     * @param string|null $typeOf
64
     * @return mixed
65
     * @throws \LogicException
66
     */
67 10
    public function scalar(string $field, string $typeOf = null)
68
    {
69 10
        $processor = $this->getRepository()->getProcessor();
0 ignored issues
show
Bug introduced by
It seems like getRepository() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
70
71 10
        $result = \array_first($processor->getArrayResult((clone $this)->limit(1)));
0 ignored issues
show
Bug introduced by
It seems like limit() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
72 10
        $result = \data_get($result, $field);
73
74 10
        if ($typeOf !== null) {
75 10
            return $this->cast($result, $typeOf);
76
        }
77
78
        return $result;
79
    }
80
81
    /**
82
     * @param mixed $result
83
     * @param string $typeOf
84
     * @return array|\Closure|object
85
     */
86 10
    private function cast($result, string $typeOf)
87
    {
88 10
        $typeOf = \strtolower($typeOf);
89
90
        switch ($typeOf) {
91 10
            case 'callable':
92
                return function (callable $applicator = null) use ($result) {
93
                    return ($applicator ?? '\\value')($result);
94
                };
95
96 10
            case 'object':
97
                return (object)$result;
98
99 10
            case 'array':
100 10
            case 'iterable':
101
                return (array)$result;
102
        }
103
104 10
        $function = $typeOf . 'val';
105
106 10
        if (! \function_exists($function)) {
107
            throw new \InvalidArgumentException('Could not cast to type ' . $typeOf);
108
        }
109
110 10
        return $function($result);
111
    }
112
113
    /**
114
     * @param string|null $field
115
     * @return int
116
     * @throws \LogicException
117
     */
118 2
    public function count(?string $field = 'id'): int
119
    {
120 2
        return $this->select('COUNT(' . $field . ') AS __count')
0 ignored issues
show
Bug introduced by
It seems like select() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
121 2
            ->scalar('__count', 'int');
122
    }
123
124
    /**
125
     * @param string|null $field
126
     * @return int
127
     * @throws \LogicException
128
     */
129 2
    public function sum(string $field = null): int
130
    {
131 2
        return $this->select('SUM(' . $field . ') AS __sum')
0 ignored issues
show
Bug introduced by
It seems like select() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
132 2
            ->scalar('__sum', 'int');
133
    }
134
135
    /**
136
     * @param string|null $field
137
     * @return int
138
     * @throws \LogicException
139
     */
140 2
    public function avg(string $field = null): int
141
    {
142 2
        return $this->select('AVG(' . $field . ') AS __avg')
0 ignored issues
show
Bug introduced by
It seems like select() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
143 2
            ->scalar('__avg', 'int');
144
    }
145
146
    /**
147
     * @param string|null $field
148
     * @return int
149
     * @throws \LogicException
150
     */
151 2
    public function max(string $field = null): int
152
    {
153 2
        return $this->select('MAX(' . $field . ') AS __max')
0 ignored issues
show
Bug introduced by
It seems like select() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
154 2
            ->scalar('__max', 'int');
155
    }
156
157
    /**
158
     * @param string|null $field
159
     * @return int
160
     * @throws \LogicException
161
     */
162 2
    public function min(string $field = null): int
163
    {
164 2
        return $this->select('MIN(' . $field . ') AS __min')
0 ignored issues
show
Bug introduced by
It seems like select() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
165 2
            ->scalar('__min', 'int');
166
    }
167
168
    /**
169
     * @param string ...$fields
170
     * @return Collection
171
     */
172 2
    public function collect(string ...$fields): Collection
173
    {
174 2
        return Collection::wrap($this->get(...$fields));
175
    }
176
177
    /**
178
     * @param string[] $fields
179
     * @return object|null
180
     * @throws \LogicException
181
     */
182
    public function first(string ...$fields)
183
    {
184
        return \array_first($this->get(...$fields));
185
    }
186
}
187