Exponential 5.x Kernel 7.5.40 Exponential New Stack (Symfony-based) Kernel — PHP Class Reference

SubtreeLimitationType.php
Go to the documentation of this file.
1 <?php
2
7 namespace eZ\Publish\Core\Limitation;
8
9 use eZ\Publish\API\Repository\Exceptions\NotFoundException as APINotFoundException;
10 use eZ\Publish\API\Repository\Values\ValueObject;
11 use eZ\Publish\API\Repository\Values\User\UserReference as APIUserReference;
12 use eZ\Publish\API\Repository\Values\Content\Content;
13 use eZ\Publish\API\Repository\Values\Content\ContentInfo;
14 use eZ\Publish\API\Repository\Values\Content\ContentCreateStruct;
15 use eZ\Publish\API\Repository\Values\Content\VersionInfo;
16 use eZ\Publish\API\Repository\Values\Content\Location;
17 use eZ\Publish\API\Repository\Values\Content\LocationCreateStruct;
18 use eZ\Publish\Core\Base\Exceptions\InvalidArgumentException;
19 use eZ\Publish\Core\Base\Exceptions\InvalidArgumentType;
20 use eZ\Publish\API\Repository\Values\User\Limitation\SubtreeLimitation as APISubtreeLimitation;
21 use eZ\Publish\API\Repository\Values\User\Limitation as APILimitationValue;
22 use eZ\Publish\SPI\Limitation\Target\Version;
23 use eZ\Publish\SPI\Limitation\Type as SPILimitationTypeInterface;
24 use eZ\Publish\Core\FieldType\ValidationError;
25 use eZ\Publish\SPI\Persistence\Content\Location as SPILocation;
26 use eZ\Publish\Core\Repository\Values\Content\Query\Criterion\PermissionSubtree;
27
31 class SubtreeLimitationType extends AbstractPersistenceLimitationType implements SPILimitationTypeInterface
32 {
42 public function acceptValue(APILimitationValue $limitationValue)
43 {
44 if (!$limitationValue instanceof APISubtreeLimitation) {
45 throw new InvalidArgumentType('$limitationValue', 'APISubtreeLimitation', $limitationValue);
46 } elseif (!is_array($limitationValue->limitationValues)) {
47 throw new InvalidArgumentType('$limitationValue->limitationValues', 'array', $limitationValue->limitationValues);
48 }
49
50 foreach ($limitationValue->limitationValues as $key => $path) {
51 if (!is_string($path)) {
52 throw new InvalidArgumentType("\$limitationValue->limitationValues[{$key}]", 'string', $path);
53 }
54 }
55 }
56
66 public function validate(APILimitationValue $limitationValue)
67 {
68 $validationErrors = [];
69 foreach ($limitationValue->limitationValues as $key => $path) {
70 try {
71 $pathArray = explode('/', trim($path, '/'));
72 $subtreeRootLocationId = end($pathArray);
73 $spiLocation = $this->persistence->locationHandler()->load($subtreeRootLocationId);
74 } catch (APINotFoundException $e) {
75 }
76
77 if (!isset($spiLocation) || strpos($spiLocation->pathString, $path) !== 0) {
78 $validationErrors[] = new ValidationError(
79 "limitationValues[%key%] => '%value%' does not exist in the backend",
80 null,
81 [
82 'value' => $path,
83 'key' => $key,
84 ]
85 );
86 }
87 }
88
89 return $validationErrors;
90 }
91
99 public function buildValue(array $limitationValues)
100 {
101 return new APISubtreeLimitation(['limitationValues' => $limitationValues]);
102 }
103
119 public function evaluate(APILimitationValue $value, APIUserReference $currentUser, ValueObject $object, array $targets = null)
120 {
121 $targets = $targets ?? [];
122
123 if (!$value instanceof APISubtreeLimitation) {
124 throw new InvalidArgumentException('$value', 'Must be of type: APISubtreeLimitation');
125 }
126
127 if ($object instanceof ContentCreateStruct) {
128 return $this->evaluateForContentCreateStruct($value, $targets);
129 } elseif ($object instanceof Content) {
130 $object = $object->getVersionInfo()->getContentInfo();
131 } elseif ($object instanceof VersionInfo) {
132 $object = $object->getContentInfo();
133 } elseif (!$object instanceof ContentInfo) {
134 // As this is Role limitation we need to signal abstain on unsupported $object
135 return self::ACCESS_ABSTAIN;
136 }
137
138 $targets = array_filter($targets, function ($target) {
139 return !$target instanceof Version;
140 });
141
142 // Load locations if no specific placement was provided
143 if (empty($targets)) {
144 if ($object->isTrashed()) {
145 $targets = $this->persistence->locationHandler()->loadLocationsByTrashContent($object->id);
146 } elseif ($object->isPublished()) {
147 $targets = $this->persistence->locationHandler()->loadLocationsByContent($object->id);
148 } else {
149 // @todo Need support for draft locations to work correctly
150 $targets = $this->persistence->locationHandler()->loadParentLocationsForDraftContent($object->id);
151 }
152 }
153
154 foreach ($targets as $target) {
155 if (!$target instanceof Location && !$target instanceof SPILocation) {
156 // As this is Role limitation we need to signal abstain on unsupported $targets
157 return self::ACCESS_ABSTAIN;
158 }
159
160 foreach ($value->limitationValues as $limitationPathString) {
161 if ($target->pathString === $limitationPathString) {
162 return true;
163 }
164 if (strpos($target->pathString, $limitationPathString) === 0) {
165 return true;
166 }
167 }
168 }
169
170 return false;
171 }
172
185 protected function evaluateForContentCreateStruct(APILimitationValue $value, array $targets)
186 {
187 // If targets is empty/null return false as user does not have access
188 // to content w/o location with this limitation
189 if (empty($targets)) {
190 return false;
191 }
192
193 $hasLocationCreateStruct = false;
194 foreach ($targets as $target) {
195 if (!$target instanceof LocationCreateStruct) {
196 continue;
197 }
198
199 $hasLocationCreateStruct = true;
200 $target = $this->persistence->locationHandler()->load($target->parentLocationId);
201
202 // For ContentCreateStruct all placements must match
203 foreach ($value->limitationValues as $limitationPathString) {
204 if ($target->pathString === $limitationPathString) {
205 continue 2;
206 }
207 if (strpos($target->pathString, $limitationPathString) === 0) {
208 continue 2;
209 }
210 }
211
212 return false;
213 }
214
215 if (false === $hasLocationCreateStruct) {
216 throw new InvalidArgumentException(
217 '$targets',
218 'If $object is ContentCreateStruct must contain objects of type: LocationCreateStruct'
219 );
220 }
221
222 return true;
223 }
224
233 public function getCriterion(APILimitationValue $value, APIUserReference $currentUser)
234 {
235 if (empty($value->limitationValues)) {
236 // no limitation values
237 throw new \RuntimeException('$value->limitationValues is empty, it should not have been stored in the first place');
238 }
239
240 if (!isset($value->limitationValues[1])) {
241 // 1 limitation value: EQ operation
242 return new PermissionSubtree($value->limitationValues[0]);
243 }
244
245 // several limitation values: IN operation
246 return new PermissionSubtree($value->limitationValues);
247 }
248
255 public function valueSchema()
256 {
257 return self::VALUE_SCHEMA_LOCATION_PATH;
258 }
259 }
eZ\Publish\API\Repository\Exceptions\NotFoundException
This Exception is thrown if an object referenced by an id or identifier could not be found in the rep...
Definition: API/Repository/Exceptions/NotFoundException.php:16
eZ\Publish\API\Repository\Values\Content\ContentCreateStruct
Definition: API/Repository/Values/Content/ContentCreateStruct.php:15
eZ\Publish\API\Repository\Values\Content\ContentInfo
Definition: API/Repository/Values/Content/ContentInfo.php:31
eZ\Publish\API\Repository\Values\Content\Content
Definition: Publish/API/Repository/Values/Content/Content.php:21
eZ\Publish\API\Repository\Values\Content\LocationCreateStruct
This class is used to create a new Location for a content object.
Definition: API/Repository/Values/Content/LocationCreateStruct.php:15
eZ\Publish\API\Repository\Values\Content\Location
Definition: API/Repository/Values/Content/Location.php:32
eZ\Publish\API\Repository\Values\Content\VersionInfo
Definition: API/Repository/Values/Content/VersionInfo.php:27
eZ\Publish\API\Repository\Values\User\Limitation\SubtreeLimitation
Definition: SubtreeLimitation.php:12
eZ\Publish\API\Repository\Values\ValueObject
Definition: API/Repository/Values/ValueObject.php:21
eZ\Publish\Core\Base\Exceptions\InvalidArgumentException
Invalid Argument Type Exception implementation.
Definition: Core/Base/Exceptions/InvalidArgumentException.php:20
eZ\Publish\Core\Base\Exceptions\InvalidArgumentType
Invalid Argument Type Exception implementation.
Definition: InvalidArgumentType.php:17
eZ\Publish\Core\FieldType\ValidationError
Class for validation errors.
Definition: Core/FieldType/ValidationError.php:17
eZ\Publish\Core\Limitation\AbstractPersistenceLimitationType
LocationLimitation is a Content limitation.
Definition: AbstractPersistenceLimitationType.php:15
eZ\Publish\Core\Limitation\SubtreeLimitationType
SubtreeLimitation is a Content Limitation & a Role Limitation.
Definition: SubtreeLimitationType.php:32
eZ\Publish\Core\Limitation\SubtreeLimitationType\validate
validate(APILimitationValue $limitationValue)
Makes sure LimitationValue->limitationValues is valid according to valueSchema().
Definition: SubtreeLimitationType.php:66
eZ\Publish\Core\Limitation\SubtreeLimitationType\buildValue
buildValue(array $limitationValues)
Create the Limitation Value.
Definition: SubtreeLimitationType.php:99
eZ\Publish\Core\Limitation\SubtreeLimitationType\getCriterion
getCriterion(APILimitationValue $value, APIUserReference $currentUser)
Returns Criterion for use in find() query.
Definition: SubtreeLimitationType.php:233
eZ\Publish\Core\Limitation\SubtreeLimitationType\acceptValue
acceptValue(APILimitationValue $limitationValue)
Accepts a Limitation value and checks for structural validity.
Definition: SubtreeLimitationType.php:42
eZ\Publish\Core\Limitation\SubtreeLimitationType\evaluate
evaluate(APILimitationValue $value, APIUserReference $currentUser, ValueObject $object, array $targets=null)
Evaluate permission against content & target(placement/parent/assignment).
Definition: SubtreeLimitationType.php:119
eZ\Publish\Core\Limitation\SubtreeLimitationType\valueSchema
valueSchema()
Returns info on valid $limitationValues.
Definition: SubtreeLimitationType.php:255
eZ\Publish\Core\Limitation\SubtreeLimitationType\evaluateForContentCreateStruct
evaluateForContentCreateStruct(APILimitationValue $value, array $targets)
Evaluate permissions for ContentCreateStruct against LocationCreateStruct placements.
Definition: SubtreeLimitationType.php:185
eZ\Publish\Core\Repository\Values\Content\Query\Criterion\PermissionSubtree
Criterion that matches content that belongs to a given (list of) Subtree(s).
Definition: Repository/Values/Content/Query/Criterion/PermissionSubtree.php:24
eZ\Publish\SPI\Limitation\Target\Version
Definition: SPI/Limitation/Target/Version.php:25
eZ\Publish\API\Repository\Values\User\UserReference
This interface represents a user reference for use in sessions and Repository.
Definition: API/Repository/Values/User/UserReference.php:13
eZ\Publish\SPI\Limitation\Type
This interface represent the Limitation Type.
Definition: SPI/Limitation/Type.php:22
eZ\Publish\SPI\Limitation\Type\ACCESS_ABSTAIN
const ACCESS_ABSTAIN
Definition: SPI/Limitation/Type.php:34
eZ\Publish\SPI\Limitation\Type\VALUE_SCHEMA_LOCATION_PATH
const VALUE_SCHEMA_LOCATION_PATH
Definition: SPI/Limitation/Type.php:44
eZ\Publish\API\Repository\Values\User\Limitation
Definition: BlockingLimitation.php:7
eZ\Publish\Core\Limitation
Definition: AbstractPersistenceLimitationType.php:7
eZ\Publish\SPI\Persistence\Content\Location
Definition: SPI/Persistence/Content/Location/CreateStruct.php:7
Copyright © 1998 – 2026 7x. All rights reserved. Licensed under the GNU GPLv2+.