Completed
Push — master ( 4fe654...d2edea )
by Daniel
04:44 queued 02:31
created

CollectionsAgent   A

Complexity

Total Complexity 14

Size/Duplication

Total Lines 122
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 7

Importance

Changes 0
Metric Value
wmc 14
lcom 1
cbo 7
dl 0
loc 122
rs 10
c 0
b 0
f 0

9 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 4 1
A supports() 0 4 1
A getCapabilities() 0 18 1
A find() 0 14 3
A save() 0 4 1
A delete() 0 4 1
A query() 0 20 2
A getIdentifier() 0 13 3
A setParent() 0 4 1
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Psi\Bridge\ObjectAgent\Doctrine\Collections;
6
7
use Doctrine\Common\Collections\Criteria;
8
use Psi\Component\ObjectAgent\AgentInterface;
9
use Psi\Component\ObjectAgent\Capabilities;
10
use Psi\Component\ObjectAgent\Exception\BadMethodCallException;
11
use Psi\Component\ObjectAgent\Exception\ObjectNotFoundException;
12
use Psi\Component\ObjectAgent\Query\Comparison;
13
use Psi\Component\ObjectAgent\Query\Query;
14
15
class CollectionsAgent implements AgentInterface
16
{
17
    private $store;
18
19
    public function __construct(Store $store)
20
    {
21
        $this->store = $store;
22
    }
23
24
    /**
25
     * {@inheritdoc}
26
     */
27
    public function supports(string $classFqn): bool
28
    {
29
        return $this->store->hasCollection($classFqn);
30
    }
31
32
    /**
33
     * {@inheritdoc}
34
     */
35
    public function getCapabilities(): Capabilities
36
    {
37
        return Capabilities::create([
38
            'can_set_parent' => false,
39
            'supported_comparators' => [
40
                Comparison::EQUALS,
41
                Comparison::NOT_EQUALS,
42
                Comparison::LESS_THAN,
43
                Comparison::LESS_THAN_EQUAL,
44
                Comparison::GREATER_THAN,
45
                Comparison::GREATER_THAN_EQUAL,
46
                Comparison::IN,
47
                Comparison::NOT_IN,
48
                Comparison::CONTAINS,
49
                Comparison::NULL,
50
            ],
51
        ]);
52
    }
53
54
    /**
55
     * {@inheritdoc}
56
     */
57
    public function find($identifier, string $classFqn = null)
58
    {
59
        if (null === $classFqn) {
60
            throw BadMethodCallException::classArgumentIsMandatory(__CLASS__);
61
        }
62
63
        $object = $this->store->find($classFqn, $identifier);
64
65
        if (null === $object) {
66
            throw ObjectNotFoundException::forClassAndIdentifier($classFqn, $identifier);
67
        }
68
69
        return $object;
70
    }
71
72
    /**
73
     * {@inheritdoc}
74
     */
75
    public function save($object)
76
    {
77
        // do nothing ...
78
    }
79
80
    /**
81
     * {@inheritdoc}
82
     */
83
    public function delete($object)
84
    {
85
        $this->store->delete($object);
86
    }
87
88
    /**
89
     * {@inheritdoc}
90
     */
91
    public function query(Query $query): \Traversable
92
    {
93
        $collection = $this->store->getCollection($query->getClassFqn());
94
95
        $doctrineExpression = null;
96
        if ($query->hasExpression()) {
97
            $expressionBuilder = Criteria::expr();
98
            $visitor = new CollectionsVisitor($expressionBuilder);
99
            $doctrineExpression = $visitor->dispatch($query->getExpression());
100
        }
101
102
        $criteria = new Criteria(
103
            $doctrineExpression,
104
            $query->getOrderings(),
105
            $query->getFirstResult(),
106
            $query->getMaxResults()
107
        );
108
109
        return $collection->matching($criteria);
110
    }
111
112
    /**
113
     * {@inheritdoc}
114
     */
115
    public function getIdentifier($object)
116
    {
117
        foreach ($this->store->getCollection(get_class($object)) as $identifier => $element) {
118
            if ($element === $object) {
119
                return $identifier;
120
            }
121
        }
122
123
        throw new \RuntimeException(sprintf(
124
            'Could not find identifier for object of class "%s"',
125
            get_class($object)
126
        ));
127
    }
128
129
    /**
130
     * {@inheritdoc}
131
     */
132
    public function setParent($object, $parent)
133
    {
134
        throw BadMethodCallException::setParentNotSupported(__CLASS__);
135
    }
136
}
137