AbstractDatabaseQuery::getReadyQuery()   B
last analyzed

Complexity

Conditions 3
Paths 4

Size

Total Lines 24
Code Lines 15

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 15
CRAP Score 3.0021

Importance

Changes 0
Metric Value
dl 0
loc 24
ccs 15
cts 16
cp 0.9375
rs 8.9713
c 0
b 0
f 0
nc 4
cc 3
eloc 15
nop 0
crap 3.0021
1
<?php
2
3
namespace Nayjest\Querying;
4
5
6
use Exception;
7
use Nayjest\Querying\Exception\ManualInterruptProcessingException;
8
use Nayjest\Querying\Handler\Priority;
9
use Nayjest\Querying\Operation\CloneOperation;
10
use Nayjest\Querying\Operation\CustomOperation;
11
use Nayjest\Querying\Operation\FetchOperation;
12
use Nayjest\Querying\Operation\SortOperation;
13
14
abstract class AbstractDatabaseQuery extends AbstractQuery
15
{
16
    abstract public function getSQL();
17
    abstract protected function getCountInternal();
18
19
    /**
20
     * AbstractDatabaseQuery constructor.
21
     * @param $dataSource
22
     * @param string $rowClass
23
     */
24 6
    public function __construct($dataSource, $rowClass)
25
    {
26 6
        parent::__construct($dataSource, $rowClass);
27 6
        $this->addOperations(
28
            [
29 6
                new CloneOperation(),
30 6
                new FetchOperation(),
31
            ]
32 6
        );
33 6
    }
34
35
    /**
36
     * Returns query builder with all database operations applied.
37
     *
38
     * @return object
39
     * @throws Exception
40
     */
41 4
    protected function getReadyQuery()
42
    {
43
44 4
        $readyQuery = null;
45 4
        $operation = new CustomOperation(
46 4
            function ($query) use (&$readyQuery) {
47 4
                $readyQuery = $query;
48 4
                throw new ManualInterruptProcessingException;
49 4
            },
50
            // before fetch
51 4
            Priority::FETCH + 1
52 4
        );
53 4
        $this->addOperation($operation);
54
        try {
55 4
            $this->get();
56 4
        } catch (ManualInterruptProcessingException $e) {
57
            // This exception is expected, don't needs further processing
58
        }
59 4
        $this->removeOperation($operation);
60 4
        if (!is_object($readyQuery)) {
61
            throw new Exception("Failed to interrupt processing for extracting query object.");
62
        }
63 4
        return $readyQuery;
64
    }
65
66
    /**
67
     * @return int
68
     */
69 2
    public function count()
70
    {
71 2
        $removed = [];
72
        /** remove sorting because it will produce invalid SQL that fails on Postgres
73
         * @see https://github.com/view-components/view-components/issues/33
74
         */
75 2
        foreach ($this->getOperations() as $operation) {
76 2
            if ($operation instanceof SortOperation) {
77
                $this->removeOperation($operation);
78
                $removed[] = $operation;
79
            }
80 2
        }
81 2
        $count = $this->getCountInternal();
82 2
        $this->addOperations($removed);
83 2
        return $count;
84
    }
85
}
86