Completed
Push — middleware-wip ( 71b03c...531d78 )
by Romain
03:32
created

PersistenceManager   A

Complexity

Total Complexity 17

Size/Duplication

Total Lines 135
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 5

Importance

Changes 0
Metric Value
wmc 17
c 0
b 0
f 0
lcom 1
cbo 5
dl 0
loc 135
rs 10

6 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 4 1
A save() 0 22 3
A fetchFirst() 0 18 4
A refreshFormIdentifier() 0 10 3
A initializePersistence() 0 10 3
A getSortedPersistence() 0 17 3
1
<?php
2
/*
3
 * 2017 Romain CANON <[email protected]>
4
 *
5
 * This file is part of the TYPO3 FormZ project.
6
 * It is free software; you can redistribute it and/or modify it
7
 * under the terms of the GNU General Public License, either
8
 * version 3 of the License, or any later version.
9
 *
10
 * For the full copyright and license information, see:
11
 * http://www.gnu.org/licenses/gpl-3.0.html
12
 */
13
14
namespace Romm\Formz\Persistence;
15
16
use Romm\Formz\Exceptions\InvalidEntryException;
17
use Romm\Formz\Form\FormInterface;
18
use Romm\Formz\Form\FormObject;
19
use Romm\Formz\Form\Service\DataObject\FormIdentifierObject;
20
21
/**
22
 * Manages persistence for a given form object.
23
 */
24
class PersistenceManager
25
{
26
    /**
27
     * @var FormObject
28
     */
29
    protected $formObject;
30
31
    /**
32
     * @var bool
33
     */
34
    protected $initializationDone = false;
35
36
    /**
37
     * @param FormObject $formObject
38
     */
39
    public function __construct(FormObject $formObject)
40
    {
41
        $this->formObject = $formObject;
42
    }
43
44
    /**
45
     * Loops on the registered persistence services and saves the given form
46
     * instance in each one.
47
     *
48
     * @param FormIdentifierObject $identifierObject
49
     * @param FormInterface        $form
50
     */
51
    public function save(FormIdentifierObject $identifierObject, FormInterface $form)
52
    {
53
        $this->initializePersistence();
54
55
        $identifierObjectBackup = clone $identifierObject;
56
57
        foreach ($this->getSortedPersistence() as $persistence) {
58
            $persistence->save($identifierObject, $form);
59
        }
60
61
        /*
62
         * Checking if the identifier hash did change during the saving process.
63
         * This can happen for instance when the form has been inserted in
64
         * database and has a new uid.
65
         *
66
         * If this does happen, we need to remove the old form identifier
67
         * instances from persistence services, and replace them by the new one.
68
         */
69
        if ($identifierObjectBackup->getIdentifierHash() !== $identifierObject->getIdentifierHash()) {
70
            $this->refreshFormIdentifier($identifierObjectBackup, $identifierObject, $form);
71
        }
72
    }
73
74
    /**
75
     * Loops on the registered persistence services, and tries to fetch the
76
     * form. If a form is found, it is returned and the loop breaks. If not form
77
     * is found, `null` is returned.
78
     *
79
     * @param FormIdentifierObject $identifierObject
80
     * @return FormInterface|null
81
     * @throws InvalidEntryException
82
     */
83
    public function fetchFirst(FormIdentifierObject $identifierObject)
84
    {
85
        $this->initializePersistence();
86
87
        foreach ($this->getSortedPersistence() as $persistence) {
88
            if ($persistence->has($identifierObject)) {
89
                $form = $persistence->fetch($identifierObject);
90
91
                if (false === $form instanceof FormInterface) {
92
                    throw InvalidEntryException::persistenceInvalidEntryFetched($persistence, $form);
93
                }
94
95
                return $form;
96
            }
97
        }
98
99
        return null;
100
    }
101
102
    /**
103
     * Will remove the old identifier objects on every persistence service that
104
     * has it, and replace it with the new identifier object.
105
     *
106
     * @param FormIdentifierObject $oldIdentifierObject
107
     * @param FormIdentifierObject $newIdentifierObject
108
     * @param FormInterface        $form
109
     */
110
    protected function refreshFormIdentifier(FormIdentifierObject $oldIdentifierObject, FormIdentifierObject $newIdentifierObject, FormInterface $form)
111
    {
112
        foreach ($this->getSortedPersistence() as $persistence) {
113
            $persistence->delete($oldIdentifierObject);
114
115
            if (false === $persistence->has($newIdentifierObject)) {
116
                $persistence->save($newIdentifierObject, $form);
117
            }
118
        }
119
    }
120
121
    /**
122
     * Loops on persistence services and initializes them.
123
     */
124
    protected function initializePersistence()
125
    {
126
        if (false === $this->initializationDone) {
127
            $this->initializationDone = true;
128
129
            foreach ($this->formObject->getConfiguration()->getPersistence() as $persistence) {
130
                $persistence->initialize();
131
            }
132
        }
133
    }
134
135
    /**
136
     * Sorts the persistence services, based on their priority property: the
137
     * ones with the highest priority will come first.
138
     *
139
     * @return PersistenceInterface[]
140
     */
141
    protected function getSortedPersistence()
142
    {
143
        $items = $this->formObject->getConfiguration()->getPersistence();
144
145
        usort($items, function (PersistenceInterface $a, PersistenceInterface $b) {
146
            $priorityA = (int)$a->getPriority();
147
            $priorityB = (int)$b->getPriority();
148
149
            if ($priorityA === $priorityB) {
150
                return 0;
151
            }
152
153
            return $priorityA < $priorityB ? 1 : -1;
154
        });
155
156
        return $items;
157
    }
158
}
159