/
ControllerTrait.php
95 lines (81 loc) · 3.78 KB
/
ControllerTrait.php
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
<?php
namespace Concrete\Core\Attribute\Key\Component\KeySelector;
use Concrete\Core\Attribute\Category\CategoryInterface;
use Concrete\Core\Attribute\Command\ClearAttributesCommand;
use Concrete\Core\Attribute\Command\SaveAttributesCommand;
use Concrete\Core\Attribute\ObjectInterface;
use Concrete\Core\Error\ErrorList\ErrorList;
use Concrete\Core\Validation\Response;
use Symfony\Component\HttpFoundation\JsonResponse;
/**
* Adds required methods to actual REST controllers.
*
* @property \Concrete\Core\Application\Application $app
* @property \Concrete\Core\Http\Request $request
*/
trait ControllerTrait
{
abstract public function getCategory(): CategoryInterface;
/**
* @return ObjectInterface[]
*/
abstract public function getObjects(): array;
abstract public function canEditAttributeKey(int $akID, ObjectInterface $object): bool;
public function saveAttributes(): ?ErrorList
{
// Let's retrieve a list of attribute keys that we're trying to set.
$selectedAttributes = (array)$this->request->request->get('selectedKeys', []);
// In case of non modified Multiple Valued attribute in bulk edit
$ignoredAttributes = (array)$this->request->request->get('ignoredKeys', []);
foreach ($this->getObjects() as $object) {
// Now, let's divide attributes into piles of those we need to save, and those we need to clear
$attributesToClear = [];
$attributesToSave = [];
$values = $this->category->getAttributeValues($object);
foreach ($values as $value) {
$attributeKey = $value->getAttributeKey();
if ($attributeKey) {
if (!in_array($attributeKey->getAttributeKeyID(), $selectedAttributes) &&
!in_array($attributeKey->getAttributeKeyID(), $ignoredAttributes) &&
$this->canEditAttributeKey($attributeKey->getAttributeKeyID(), $object)) {
// This is an attribute we have currently set on the object, but it's not
// in the request, and it is something we're allowed to edit, so that means it needs
// to be cleared
$attributesToClear[] = $attributeKey;
}
}
}
foreach ($selectedAttributes as $akID) {
if ($this->canEditAttributeKey($akID, $object)) {
$ak = $this->category->getAttributeKeyByID($akID);
if ($ak) {
$controller = $ak->getController();
$validator = $controller->getValidator();
/**
* @var $response Response
*/
$response = $validator->validateSaveValueRequest(
$controller,
$this->request,
false // In this case we should allow field not present errors because we're not on registration or in user profile
);
if ($response->isValid()) {
$attributesToSave[] = $ak;
} else {
return $response->getErrorObject();
}
}
}
}
$this->app->executeCommand(new ClearAttributesCommand($attributesToClear, $object));
$this->app->executeCommand(new SaveAttributesCommand($attributesToSave, $object));
}
return null;
}
public function getAttribute()
{
$key = $this->category->getByID($this->request->request->get('akID'));
$keySerializer = new KeySerializer($key);
return new JsonResponse($keySerializer);
}
}