Completed
Push — master ( 11b317...37df4d )
by Lucas
09:27
created

ReadOnlyValidator   A

Complexity

Total Complexity 8

Size/Duplication

Total Lines 74
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 3

Test Coverage

Coverage 0%

Importance

Changes 0
Metric Value
wmc 8
lcom 1
cbo 3
dl 0
loc 74
ccs 0
cts 38
cp 0
rs 10
c 0
b 0
f 0

3 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 4 1
B validate() 0 27 4
A getStoredValueByPath() 0 16 3
1
<?php
2
/**
3
 * Validator for read only
4
 */
5
6
namespace Graviton\RestBundle\Validator\Constraints\ReadOnly;
7
8
use Symfony\Component\Validator\Constraint;
9
use Symfony\Component\Validator\ConstraintValidator;
10
use Doctrine\ODM\MongoDB\DocumentManager;
11
use Graviton\I18nBundle\Document\TranslatableDocumentInterface;
12
13
/**
14
 * Validator for read only
15
 *
16
 * @author   List of contributors <https://github.com/libgraviton/graviton/graphs/contributors>
17
 * @license  http://opensource.org/licenses/gpl-license.php GNU Public License
18
 * @link     http://swisscom.ch
19
 */
20
class ReadOnlyValidator extends ConstraintValidator
21
{
22
    private $dm;
23
24
    /**
25
     * Creates a new ReadOnlyValidator instance
26
     *
27
     * @param DocumentManager $dm Document manager
28
     */
29
    public function __construct(DocumentManager $dm)
30
    {
31
        $this->dm = $dm;
32
    }
33
34
    /**
35
     * Checks read only
36
     *
37
     * @param string     $value      Input value
38
     * @param Constraint $constraint Constraint instance
39
     *
40
     * @return void
41
     */
42
    public function validate($value, Constraint $constraint)
43
    {
44
        $submittedData = $this->context->getRoot()->getData();
45
46
        // if the structure is nested it can't access the id via getObject()
47
        $recordClass = get_class($submittedData);
48
        $recordId = $this->context->getRoot()->getData()->getId();
49
50
        $record = $this->dm->find($recordClass, $recordId);
51
52
        if ($record) {
53
            $storedValue = $this->getStoredValueByPath($this->context->getPropertyPath(), $record);
54
55
            if ($storedValue instanceof \DateTime) {
56
                $isEqual = ($storedValue == $value);
57
            } else {
58
                $isEqual = ($value === $storedValue);
59
            }
60
61
            if (!$isEqual) {
62
                $this->context->addViolation(
63
                    $constraint->message,
64
                    array('%string%' => $this->context->getPropertyPath())
65
                );
66
            }
67
        }
68
    }
69
70
    /**
71
     * Gets the stored value from a path
72
     *
73
     * @param string                        $path   Value path
74
     * @param TranslatableDocumentInterface $record Record
75
     * @return mixed
76
     */
77
    public function getStoredValueByPath($path, $record)
78
    {
79
        $path = explode('.', $path);
80
81
        $pathCount = count($path);
82
83
        for ($i = 1; $i < $pathCount; $i++) {
84
            if (is_int($path[$i])) {
85
                $record = $record[$path[$i]];
86
            } else {
87
                $record = $record->{'get' . $path[$i]}();
88
            }
89
        }
90
91
        return $record;
92
    }
93
}
94