GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.
Completed
Pull Request — master (#10)
by
unknown
13:47 queued 06:22
created

ObjectService   F

Complexity

Total Complexity 96

Size/Duplication

Total Lines 905
Duplicated Lines 22.43 %

Coupling/Cohesion

Components 1
Dependencies 14

Test Coverage

Coverage 89.24%

Importance

Changes 22
Bugs 2 Features 6
Metric Value
c 22
b 2
f 6
dl 203
loc 905
wmc 96
lcom 1
cbo 14
ccs 282
cts 316
cp 0.8924
rs 1.5999

20 Methods

Rating   Name   Duplication   Size   Complexity  
A appendContentStream() 0 10 1
A bulkUpdateProperties() 0 10 1
C createDocument() 14 66 10
C createDocumentFromSource() 19 49 7
B createFolder() 29 29 3
B createItem() 5 34 4
A createPolicy() 0 11 1
B createRelationship() 28 28 3
D deleteContentStream() 12 38 9
A deleteObject() 0 16 2
B deleteTree() 0 26 4
A getAllowableActions() 0 4 1
B getContentStream() 0 32 6
C getObject() 36 36 7
C getObjectByPath() 36 36 7
B getProperties() 0 27 4
B getRenditions() 0 32 4
B moveObject() 0 25 3
D setContentStream() 12 45 10
D updateProperties() 12 35 9

How to fix   Duplicated Code    Complexity   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

Complex Class

 Tip:   Before tackling complexity, make sure that you eliminate any duplication first. This often can reduce the size of classes significantly.

Complex classes like ObjectService often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes. You can also have a look at the cohesion graph to spot any un-connected, or weakly-connected components.

Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.

While breaking up the class, it is a good idea to analyze how other classes use ObjectService, and based on these observations, apply Extract Interface, too.

1
<?php
2
namespace Dkd\PhpCmis\Bindings\Browser;
3
4
/**
5
 * This file is part of php-cmis-lib.
6
 *
7
 * (c) Sascha Egerer <[email protected]>
8
 *
9
 * For the full copyright and license information, please view the LICENSE
10
 * file that was distributed with this source code.
11
 */
12
13
use Dkd\PhpCmis\Constants;
14
use Dkd\PhpCmis\Data\AclInterface;
15
use Dkd\PhpCmis\Data\AllowableActionsInterface;
16
use Dkd\PhpCmis\Data\BulkUpdateObjectIdAndChangeTokenInterface;
17
use Dkd\PhpCmis\Data\ExtensionDataInterface;
18
use Dkd\PhpCmis\Data\FailedToDeleteDataInterface;
19
use Dkd\PhpCmis\Data\ObjectDataInterface;
20
use Dkd\PhpCmis\Data\PropertiesInterface;
21
use Dkd\PhpCmis\Data\RenditionDataInterface;
22
use Dkd\PhpCmis\Enum\IncludeRelationships;
23
use Dkd\PhpCmis\Enum\UnfileObject;
24
use Dkd\PhpCmis\Enum\VersioningState;
25
use Dkd\PhpCmis\Exception\CmisInvalidArgumentException;
26
use Dkd\PhpCmis\ObjectServiceInterface;
27
use Dkd\PhpCmis\PropertyIds;
28
use Dkd\PhpCmis\SessionParameter;
29
use GuzzleHttp\Post\PostFile;
30
use GuzzleHttp\Stream\LimitStream;
31
use GuzzleHttp\Message\Response;
32
use GuzzleHttp\Stream\StreamInterface;
33
34
/**
35
 * Object Service Browser Binding client.
36
 */
37
class ObjectService extends AbstractBrowserBindingService implements ObjectServiceInterface
38
{
39
    /**
40
     * Appends the content stream to the content of the document.
41
     *
42
     * The stream in contentStream is consumed but not closed by this method.
43
     *
44
     * @param string $repositoryId the identifier for the repository
45
     * @param string $objectId The identifier for the object. The repository might return a different/new object id
46
     * @param StreamInterface $contentStream The content stream to append
47
     * @param boolean $isLastChunk Indicates if this content stream is the last chunk
48
     * @param string|null $changeToken The last change token of this object that the client received.
49
     *      The repository might return a new change token (default is <code>null</code>)
50
     * @param ExtensionDataInterface|null $extension
51
     */
52
    public function appendContentStream(
53
        $repositoryId,
54
        & $objectId,
55
        StreamInterface $contentStream,
56
        $isLastChunk,
57
        & $changeToken = null,
58
        ExtensionDataInterface $extension = null
59
    ) {
60
        // TODO: Implement appendContentStream() method.
61
    }
62
63
    /**
64
     * Updates properties and secondary types of one or more objects.
65
     *
66
     * @param string $repositoryId the identifier for the repository
67
     * @param BulkUpdateObjectIdAndChangeTokenInterface[] $objectIdsAndChangeTokens
68
     * @param PropertiesInterface $properties
69
     * @param string[] $addSecondaryTypeIds the secondary types to apply
70
     * @param string[] $removeSecondaryTypeIds the secondary types to remove
71
     * @param ExtensionDataInterface|null $extension
72
     * @return BulkUpdateObjectIdAndChangeTokenInterface[]
73
     */
74
    public function bulkUpdateProperties(
75
        $repositoryId,
76
        array $objectIdsAndChangeTokens,
77
        PropertiesInterface $properties,
78
        array $addSecondaryTypeIds,
79
        array $removeSecondaryTypeIds,
80
        ExtensionDataInterface $extension = null
81
    ) {
82
        // TODO: Implement bulkUpdateProperties() method.
83
    }
84
85
    /**
86
     * Creates a document object of the specified type (given by the cmis:objectTypeId property)
87
     * in the (optionally) specified location.
88
     *
89
     * @param string $repositoryId the identifier for the repository
90
     * @param PropertiesInterface $properties the property values that must be applied to the newly
91
     *      created document object
92
     * @param string|null $folderId if specified, the identifier for the folder that must be the parent
93
     *      folder for the newly created document object
94
     * @param StreamInterface|null $contentStream the content stream that must be stored for the newly
95
     *      created document object
96
     * @param VersioningState|null $versioningState specifies what the versioning state of the newly created object
97
     *      must be (default is <code>VersioningState::MAJOR</code>)
98
     * @param string[] $policies a list of policy IDs that must be applied to the newly created document object
99
     * @param AclInterface|null $addAces a list of ACEs that must be added to the newly created document object,
100
     *      either using the ACL from folderId if specified, or being applied if no folderId is specified
101
     * @param AclInterface|null $removeAces a list of ACEs that must be removed from the newly created document object,
102
     *      either using the ACL from folderId if specified, or being ignored if no folderId is specified
103
     * @param ExtensionDataInterface|null $extension
104
     * @return string|null Returns the new object id or <code>null</code> if the repository sent an empty
105
     *      result (which should not happen)
106
     */
107 3
    public function createDocument(
108
        $repositoryId,
109
        PropertiesInterface $properties,
110
        $folderId = null,
111
        StreamInterface $contentStream = null,
112
        VersioningState $versioningState = null,
113
        array $policies = array(),
114
        AclInterface $addAces = null,
115
        AclInterface $removeAces = null,
116
        ExtensionDataInterface $extension = null
117
    ) {
118 3
        if ($folderId === null) {
119 1
            $url = $this->getRepositoryUrl($repositoryId);
120 1
        } else {
121 2
            $url = $this->getObjectUrl($repositoryId, $folderId);
122
        }
123
124
        // Guzzle gets the mime type for a file by the filename extension. Sometimes the filename does not contain
125
        // the correct filename extension for example when a file is uploaded in php it gets a temporary name without
126
        // a file extension. If the filename does not contain a file extension we use the given 'cmis:name' property
127
        // as filename. See also https://github.com/guzzle/guzzle/issues/571
128 3
        if ($contentStream !== null && pathinfo($contentStream->getMetadata('uri'), PATHINFO_EXTENSION) === '') {
129 1
            $contentStream = new PostFile(
130 1
                'content',
131 1
                $contentStream,
132 1
                $properties->getProperties()['cmis:name']->getFirstValue()
133 1
            );
134 1
        }
135
136 3
        $queryArray = array_replace(
137
			array(
138 3
				Constants::CONTROL_CMISACTION => Constants::CMISACTION_CREATE_DOCUMENT,
139 3
				Constants::PARAM_SUCCINCT => $this->getSuccinct() ? 'true' : 'false',
140 3
			),
141 3
			$this->convertPropertiesToQueryArray($properties),
142 3
			$this->convertPolicyIdArrayToQueryArray($policies)
143 3
		);
144 3
		if ($contentStream) {
145 2
			$queryArray['content'] = $contentStream;
146 2
		}
147 3 View Code Duplication
		if (!empty($removeAces)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
148 2
			$queryArray = array_replace($queryArray, $this->convertAclToQueryArray(
149 2
				$removeAces,
150 2
				Constants::CONTROL_REMOVE_ACE_PRINCIPAL,
151
				Constants::CONTROL_REMOVE_ACE_PERMISSION
152 2
			));
153 2
		}
154 3 View Code Duplication
		if (!empty($addAces)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
155 2
			$queryArray = array_replace($queryArray, $this->convertAclToQueryArray(
156 2
				$addAces,
157 2
				Constants::CONTROL_ADD_ACE_PRINCIPAL,
158
				Constants::CONTROL_ADD_ACE_PERMISSION
159 2
			));
160 2
		}
161 3
        if ($versioningState !== null) {
162 2
            $queryArray[Constants::PARAM_VERSIONING_STATE] = (string) $versioningState;
163 2
        }
164 3
        $responseData = $this->post(
165 3
            $url,
166
            $queryArray
167 3
        )->json();
168
169 3
        $newObject = $this->getJsonConverter()->convertObject($responseData);
170
171 3
        return ($newObject === null) ? null : $newObject->getId();
172
    }
173
174
    /**
175
     * Creates a document object as a copy of the given source document in the (optionally) specified location.
176
     *
177
     * @param string $repositoryId the identifier for the repository
178
     * @param string $sourceId the identifier for the source document
179
     * @param PropertiesInterface $properties the property values that must be applied to the newly
180
     *      created document object
181
     * @param string|null $folderId if specified, the identifier for the folder that must be the parent folder for the
182
     *      newly created document object
183
     * @param VersioningState|null $versioningState specifies what the versioning state of the newly created object
184
     *      must be (default is <code>VersioningState::MAJOR</code>)
185
     * @param string[] $policies a list of policy IDs that must be applied to the newly created document object
186
     * @param AclInterface|null $addAces a list of ACEs that must be added to the newly created document object,
187
     *      either using the ACL from folderId if specified, or being applied if no folderId is specified
188
     * @param AclInterface|null $removeAces a list of ACEs that must be removed from the newly created document object,
189
     *      either using the ACL from folderId if specified, or being ignored if no folderId is specified
190
     * @param ExtensionDataInterface|null $extension
191
     * @return string|null Returns the new object id or <code>null</code> if the repository sent an empty
192
     *      result (which should not happen)
193
     */
194 2
    public function createDocumentFromSource(
195
        $repositoryId,
196
        $sourceId,
197
        PropertiesInterface $properties,
198
        $folderId = null,
199
        VersioningState $versioningState = null,
200
        array $policies = array(),
201
        AclInterface $addAces = null,
202
        AclInterface $removeAces = null,
203
        ExtensionDataInterface $extension = null
204
    ) {
205 2 View Code Duplication
        if ($folderId === null) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
206
            $url = $this->getRepositoryUrl($repositoryId);
207
        } else {
208 2
            $url = $this->getObjectUrl($repositoryId, $folderId);
209
        }
210
211 2
		$queryArray = array_replace(
212
			array(
213 2
				Constants::CONTROL_CMISACTION => Constants::CMISACTION_CREATE_DOCUMENT_FROM_SOURCE,
214 2
				Constants::PARAM_SUCCINCT => $this->getSuccinct() ? 'true' : 'false',
215 2
                Constants::PARAM_SOURCE_ID => (string) $sourceId
216 2
			),
217 2
			$this->convertPropertiesToQueryArray($properties),
218 2
			$this->convertPolicyIdArrayToQueryArray($policies)
219 2
		);
220 2 View Code Duplication
		if (!empty($removeAces)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
221 1
			$queryArray = array_replace($queryArray, $this->convertAclToQueryArray(
222 1
				$removeAces,
223 1
				Constants::CONTROL_REMOVE_ACE_PRINCIPAL,
224
				Constants::CONTROL_REMOVE_ACE_PERMISSION
225 1
			));
226 1
		}
227 2 View Code Duplication
		if (!empty($addAces)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
228 1
			$queryArray = array_replace($queryArray, $this->convertAclToQueryArray(
229 1
				$addAces,
230 1
				Constants::CONTROL_ADD_ACE_PRINCIPAL,
231
				Constants::CONTROL_ADD_ACE_PERMISSION
232 1
			));
233 1
		}
234 2
		if ($versioningState !== null) {
235 1
			$queryArray[Constants::PARAM_VERSIONING_STATE] = (string) $versioningState;
236 1
		}
237 2
        $responseData = $this->post($url, $queryArray)->json();
238
239 2
        $newObject = $this->getJsonConverter()->convertObject($responseData);
240
241 2
        return ($newObject === null) ? null : $newObject->getId();
242
    }
243
244
    /**
245
     * Creates a folder object of the specified type (given by the cmis:objectTypeId property) in
246
     * the specified location.
247
     *
248
     * @param string $repositoryId the identifier for the repository
249
     * @param PropertiesInterface $properties the property values that must be applied to the newly
250
     *      created document object
251
     * @param string $folderId if specified, the identifier for the folder that must be the parent folder for the
252
     *      newly created document object
253
     * @param string[] $policies a list of policy IDs that must be applied to the newly created document object
254
     * @param AclInterface|null $addAces a list of ACEs that must be added to the newly created document object,
255
     *      either using the ACL from folderId if specified, or being applied if no folderId is specified
256
     * @param AclInterface|null $removeAces a list of ACEs that must be removed from the newly created document object,
257
     *      either using the ACL from folderId if specified, or being ignored if no folderId is specified
258
     * @param ExtensionDataInterface|null $extension
259
     * @return string|null Returns the new object id or <code>null</code> if the repository sent an empty
260
     *      result (which should not happen)
261
     */
262 2 View Code Duplication
    public function createFolder(
263
        $repositoryId,
264
        PropertiesInterface $properties,
265
        $folderId,
266
        array $policies = array(),
267
        AclInterface $addAces = null,
268
        AclInterface $removeAces = null,
269
        ExtensionDataInterface $extension = null
270
    ) {
271 2
        $url = $this->getObjectUrl($repositoryId, $folderId);
272 2
        $url->getQuery()->modify(
273
            array(
274 2
                Constants::CONTROL_CMISACTION => Constants::CMISACTION_CREATE_FOLDER,
275 2
                Constants::PARAM_SUCCINCT => $this->getSuccinct() ? 'true' : 'false'
276 2
            )
277 2
        );
278
279 2
        $url->getQuery()->modify($this->convertPropertiesToQueryArray($properties));
280
281 2
        $this->appendPoliciesToUrl($url, $policies);
282 2
        $this->appendAddAcesToUrl($url, $addAces);
283 2
        $this->appendRemoveAcesToUrl($url, $removeAces);
284
285 2
        $responseData = $this->post($url)->json();
286
287 2
        $newObject = $this->getJsonConverter()->convertObject($responseData);
288
289 2
        return ($newObject === null) ? null : $newObject->getId();
290
    }
291
292
    /**
293
     * Creates an item object of the specified type (given by the cmis:objectTypeId property).
294
     *
295
     * @param string $repositoryId The identifier for the repository
296
     * @param PropertiesInterface $properties The property values that must be applied to the newly
297
     *      created document object
298
     * @param string|null $folderId If specified, the identifier for the folder that must be the parent folder for the
299
     *      newly created document object
300
     * @param string[] $policies A list of policy IDs that must be applied to the newly created document object
301
     * @param AclInterface|null $addAces A list of ACEs that must be added to the newly created document object,
302
     *      either using the ACL from folderId if specified, or being applied if no folderId is specified
303
     * @param AclInterface|null $removeAces A list of ACEs that must be removed from the newly created document object,
304
     *      either using the ACL from folderId if specified, or being ignored if no folderId is specified
305
     * @param ExtensionDataInterface|null $extension
306
     * @return string|null Returns the new item id or <code>null</code> if the repository sent an empty
307
     *      result (which should not happen)
308
     */
309 2
    public function createItem(
310
        $repositoryId,
311
        PropertiesInterface $properties,
312
        $folderId = null,
313
        array $policies = array(),
314
        AclInterface $addAces = null,
315
        AclInterface $removeAces = null,
316
        ExtensionDataInterface $extension = null
317
    ) {
318 2 View Code Duplication
        if ($folderId === null) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
319
            $url = $this->getRepositoryUrl($repositoryId);
320
        } else {
321 2
            $url = $this->getObjectUrl($repositoryId, $folderId);
322
        }
323
324 2
        $url->getQuery()->modify(
325
            array(
326 2
                Constants::CONTROL_CMISACTION => Constants::CMISACTION_CREATE_ITEM,
327 2
                Constants::PARAM_SUCCINCT => $this->getSuccinct() ? 'true' : 'false'
328 2
            )
329 2
        );
330
331 2
        $url->getQuery()->modify($this->convertPropertiesToQueryArray($properties));
332
333 2
        $this->appendPoliciesToUrl($url, $policies);
334 2
        $this->appendAddAcesToUrl($url, $addAces);
335 2
        $this->appendRemoveAcesToUrl($url, $removeAces);
336
337 2
        $responseData = $this->post($url)->json();
338
339 2
        $newObject = $this->getJsonConverter()->convertObject($responseData);
340
341 2
        return ($newObject === null) ? null : $newObject->getId();
342
    }
343
344
    /**
345
     * Creates a policy object of the specified type (given by the cmis:objectTypeId property).
346
     *
347
     * @param string $repositoryId The identifier for the repository
348
     * @param PropertiesInterface $properties The property values that must be applied to the newly
349
     *      created document object
350
     * @param string|null $folderId If specified, the identifier for the folder that must be the parent folder for the
351
     *      newly created document object
352
     * @param string[] $policies A list of policy IDs that must be applied to the newly created document object
353
     * @param AclInterface|null $addAces A list of ACEs that must be added to the newly created document object,
354
     *      either using the ACL from folderId if specified, or being applied if no folderId is specified
355
     * @param AclInterface|null $removeAces A list of ACEs that must be removed from the newly created document object,
356
     *      either using the ACL from folderId if specified, or being ignored if no folderId is specified
357
     * @param ExtensionDataInterface|null $extension
358
     * @return string The id of the newly-created policy.
359
     */
360
    public function createPolicy(
361
        $repositoryId,
362
        PropertiesInterface $properties,
363
        $folderId = null,
364
        array $policies = array(),
365
        AclInterface $addAces = null,
366
        AclInterface $removeAces = null,
367
        ExtensionDataInterface $extension = null
368
    ) {
369
        // TODO: Implement createPolicy() method.
370
    }
371
372
    /**
373
     * Creates a relationship object of the specified type (given by the cmis:objectTypeId property).
374
     *
375
     * @param string $repositoryId the identifier for the repository
376
     * @param PropertiesInterface $properties the property values that must be applied to the newly
377
     *      created document object
378
     * @param string[] $policies a list of policy IDs that must be applied to the newly created document object
379
     * @param AclInterface|null $addAces a list of ACEs that must be added to the newly created document object,
380
     *      either using the ACL from folderId if specified, or being applied if no folderId is specified
381
     * @param AclInterface|null $removeAces a list of ACEs that must be removed from the newly created document object,
382
     *      either using the ACL from folderId if specified, or being ignored if no folderId is specified
383
     * @param ExtensionDataInterface|null $extension
384
     * @return string|null Returns the new item id of the relationship object or <code>null</code> if the repository
385
     *      sent an empty result (which should not happen)
386
     */
387 View Code Duplication
    public function createRelationship(
388
        $repositoryId,
389
        PropertiesInterface $properties,
390
        array $policies = array(),
391
        AclInterface $addAces = null,
392
        AclInterface $removeAces = null,
393
        ExtensionDataInterface $extension = null
394
    ) {
395
        $url = $this->getRepositoryUrl($repositoryId);
396
397
        $url->getQuery()->modify(
398
            array(
399
                Constants::CONTROL_CMISACTION => Constants::CMISACTION_CREATE_RELATIONSHIP,
400
                Constants::PARAM_SUCCINCT => $this->getSuccinct() ? 'true' : 'false'
401
            )
402
        );
403
404
        $url->getQuery()->modify($this->convertPropertiesToQueryArray($properties));
405
        $this->appendPoliciesToUrl($url, $policies);
406
        $this->appendAddAcesToUrl($url, $addAces);
407
        $this->appendRemoveAcesToUrl($url, $removeAces);
408
409
        $responseData = $this->post($url)->json();
410
411
        $newObject = $this->getJsonConverter()->convertObject($responseData);
412
413
        return ($newObject === null) ? null : $newObject->getId();
414
    }
415
416
    /**
417
     * Deletes the content stream for the specified document object.
418
     *
419
     * @param string $repositoryId the identifier for the repository
420
     * @param string $objectId the identifier for the object. The repository might return a different/new object id
421
     * @param string|null $changeToken the last change token of this object that the client received.
422
     *      The repository might return a new change token (default is <code>null</code>)
423
     * @param ExtensionDataInterface|null $extension
424
     * @throws CmisInvalidArgumentException If $objectId is empty
425
     */
426 3
    public function deleteContentStream(
427
        $repositoryId,
428
        & $objectId,
429
        & $changeToken = null,
430
        ExtensionDataInterface $extension = null
431
    ) {
432 3
        if (empty($objectId)) {
433
            throw new CmisInvalidArgumentException('Object id must not be empty!');
434
        }
435
436 3
        $url = $this->getObjectUrl($repositoryId, $objectId);
437
438 3
        $url->getQuery()->modify(
439
            array(
440 3
                Constants::CONTROL_CMISACTION => Constants::CMISACTION_DELETE_CONTENT,
441 3
                Constants::PARAM_SUCCINCT => $this->getSuccinct() ? 'true' : 'false'
442 3
            )
443 3
        );
444
445 3 View Code Duplication
        if ($changeToken !== null && !$this->getSession()->get(SessionParameter::OMIT_CHANGE_TOKENS, false)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
446 1
            $url->getQuery()->modify(array(Constants::PARAM_CHANGE_TOKEN => $changeToken));
447 1
        }
448
449 3
        $responseData = $this->post($url)->json();
450 3
        $newObject = $this->getJsonConverter()->convertObject($responseData);
451
452
        // $objectId was passed by reference. The value is changed here to new object id
453 3
        $objectId = null;
454 3 View Code Duplication
        if ($newObject !== null) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
455 3
            $objectId = $newObject->getId();
456 3
            $newObjectProperties = $newObject->getProperties()->getProperties();
457 3
            if ($changeToken !== null && count($newObjectProperties) > 0) {
458 2
                $newChangeToken = $newObjectProperties[PropertyIds::CHANGE_TOKEN];
459
                // $changeToken was passed by reference. The value is changed here
460 2
                $changeToken = $newChangeToken === null ? null : $newChangeToken->getFirstValue();
461 2
            }
462 3
        }
463 3
    }
464
465
    /**
466
     * Deletes the specified object.
467
     *
468
     * @param string $repositoryId the identifier for the repository
469
     * @param string $objectId the identifier for the object
470
     * @param boolean $allVersions If <code>true</code> then delete all versions of the document, otherwise delete only
471
     *      the document object specified (default is <code>true</code>)
472
     * @param ExtensionDataInterface|null $extension
473
     */
474 2
    public function deleteObject(
475
        $repositoryId,
476
        $objectId,
477
        $allVersions = true,
478
        ExtensionDataInterface $extension = null
479
    ) {
480 2
        $url = $this->getObjectUrl($repositoryId, $objectId);
481 2
        $url->getQuery()->modify(
482
            array(
483 2
                Constants::CONTROL_CMISACTION => Constants::CMISACTION_DELETE,
484 2
                Constants::PARAM_ALL_VERSIONS => $allVersions ? 'true' : 'false',
485
            )
486 2
        );
487
488 2
        $this->post($url);
489 2
    }
490
491
    /**
492
     * Deletes the specified folder object and all of its child- and descendant-objects.
493
     *
494
     * @param string $repositoryId the identifier for the repository
495
     * @param string $folderId the identifier for the folder
496
     * @param boolean $allVersions If <code>true</code> then delete all versions of the document, otherwise delete only
497
     *      the document object specified (default is <code>true</code>)
498
     * @param UnfileObject|null $unfileObjects defines how the repository must process file-able child- or
499
     *      descendant-objects (default is <code>UnfileObject::DELETE</code>)
500
     * @param boolean $continueOnFailure If <code>true</code>, then the repository should continue attempting to
501
     *      perform this operation even if deletion of a child- or descendant-object in the specified folder cannot
502
     *      be deleted
503
     * @param ExtensionDataInterface|null $extension
504
     * @return FailedToDeleteDataInterface Returns a list of object ids that could not be deleted
505
     */
506 4
    public function deleteTree(
507
        $repositoryId,
508
        $folderId,
509
        $allVersions = true,
510
        UnfileObject $unfileObjects = null,
511
        $continueOnFailure = false,
512
        ExtensionDataInterface $extension = null
513
    ) {
514 4
        $url = $this->getObjectUrl($repositoryId, $folderId);
515 4
        $url->getQuery()->modify(
516
            array(
517 4
                Constants::CONTROL_CMISACTION => Constants::CMISACTION_DELETE_TREE,
518 4
                Constants::PARAM_FOLDER_ID => $folderId,
519 4
                Constants::PARAM_ALL_VERSIONS => $allVersions ? 'true' : 'false',
520 4
                Constants::PARAM_CONTINUE_ON_FAILURE => $continueOnFailure ? 'true' : 'false'
521 4
            )
522 4
        );
523
524 4
        if ($unfileObjects !== null) {
525 1
            $url->getQuery()->modify(array(Constants::PARAM_UNFILE_OBJECTS => (string) $unfileObjects));
526 1
        }
527
528 4
        $response = $this->post($url);
529
530 4
        return $this->getJsonConverter()->convertFailedToDelete((array) $response->json());
531
    }
532
533
    /**
534
     * Gets the list of allowable actions for an object.
535
     *
536
     * @param string $repositoryId the identifier for the repository
537
     * @param string $objectId the identifier for the object
538
     * @param ExtensionDataInterface|null $extension
539
     * @return AllowableActionsInterface
540
     */
541
    public function getAllowableActions($repositoryId, $objectId, ExtensionDataInterface $extension = null)
542
    {
543
        // TODO: Implement getAllowableActions() method.
544
    }
545
546
    /**
547
     * Gets the content stream for the specified document object, or gets a rendition stream for
548
     * a specified rendition of a document or folder object.
549
     *
550
     * @param string $repositoryId the identifier for the repository
551
     * @param string $objectId the identifier for the object
552
     * @param string|null $streamId The identifier for the rendition stream, when used to get a rendition stream.
553
     *      For documents, if not provided then this method returns the content stream. For folders,
554
     *      it MUST be provided.
555
     * @param integer|null $offset
556
     * @param integer|null $length
557
     * @param ExtensionDataInterface|null $extension
558
     * @return StreamInterface|null
559
     * @throws CmisInvalidArgumentException If object id is empty
560
     */
561 3
    public function getContentStream(
562
        $repositoryId,
563
        $objectId,
564
        $streamId = null,
565
        $offset = null,
566
        $length = null,
567
        ExtensionDataInterface $extension = null
568
    ) {
569 3
        if (empty($objectId)) {
570
            throw new CmisInvalidArgumentException('Object id must not be empty!');
571
        }
572
573 3
        $url = $this->getObjectUrl($repositoryId, $objectId, Constants::SELECTOR_CONTENT);
574
575 3
        if ($streamId !== null) {
576 1
            $url->getQuery()->modify(array(Constants::PARAM_STREAM_ID => $streamId));
577 1
        }
578
579
        /** @var Response $response */
580 3
        $response = $this->getHttpInvoker()->get($url);
581
582 3
        $contentStream = $response->getBody();
583 3
        if (!$contentStream instanceof StreamInterface) {
584
            return null;
585
        }
586
587 3
        if ($offset !== null) {
588 1
            $contentStream = new LimitStream($contentStream, $length !== null ? $length : - 1, $offset);
589 1
        }
590
591 3
        return $contentStream;
592
    }
593
594
    /**
595
     * Gets the specified information for the object specified by id.
596
     *
597
     * @param string $repositoryId the identifier for the repository
598
     * @param string $objectId the identifier for the object
599
     * @param string|null $filter a comma-separated list of query names that defines which properties must be
600
     *      returned by the repository (default is repository specific)
601
     * @param boolean $includeAllowableActions if <code>true</code>, then the repository must return the allowable
602
     *      actions for the object (default is <code>false</code>)
603
     * @param IncludeRelationships|null $includeRelationships indicates what relationships in which the objects
604
     *      participate must be returned (default is <code>IncludeRelationships::NONE</code>)
605
     * @param string $renditionFilter indicates what set of renditions the repository must return whose kind
606
     *      matches this filter (default is "cmis:none")
607
     * @param boolean $includePolicyIds if <code>true</code>, then the repository must return the policy ids for
608
     *      the object (default is <code>false</code>)
609
     * @param boolean $includeAcl if <code>true</code>, then the repository must return the ACL for the object
610
     *      (default is <code>false</code>)
611
     * @param ExtensionDataInterface|null $extension
612
     * @return ObjectDataInterface|null Returns object of type ObjectDataInterface or <code>null</code>
613
     *     if the repository response was empty
614
     */
615 3 View Code Duplication
    public function getObject(
616
        $repositoryId,
617
        $objectId,
618
        $filter = null,
619
        $includeAllowableActions = false,
620
        IncludeRelationships $includeRelationships = null,
621
        $renditionFilter = Constants::RENDITION_NONE,
622
        $includePolicyIds = false,
623
        $includeAcl = false,
624
        ExtensionDataInterface $extension = null
625
    ) {
626 3
        $url = $this->getObjectUrl($repositoryId, $objectId, Constants::SELECTOR_OBJECT);
627 3
        $url->getQuery()->modify(
628
            array(
629 3
                Constants::PARAM_ALLOWABLE_ACTIONS => $includeAllowableActions ? 'true' : 'false',
630 3
                Constants::PARAM_RENDITION_FILTER => $renditionFilter,
631 3
                Constants::PARAM_POLICY_IDS => $includePolicyIds ? 'true' : 'false',
632 3
                Constants::PARAM_ACL => $includeAcl ? 'true' : 'false',
633 3
                Constants::PARAM_SUCCINCT => $this->getSuccinct() ? 'true' : 'false',
634 3
                Constants::PARAM_DATETIME_FORMAT => (string) $this->getDateTimeFormat()
635 3
            )
636 3
        );
637
638 3
        if (!empty($filter)) {
639 2
            $url->getQuery()->modify(array(Constants::PARAM_FILTER => (string) $filter));
640 2
        }
641
642 3
        if ($includeRelationships !== null) {
643 2
            $url->getQuery()->modify(array(Constants::PARAM_RELATIONSHIPS => (string) $includeRelationships));
644 2
        }
645
646 3
        $responseData = $this->read($url)->json();
647
648
        // TODO: Implement Cache
649 3
        return $this->getJsonConverter()->convertObject($responseData);
650
    }
651
652
    /**
653
     * Gets the specified information for the object specified by path.
654
     *
655
     * @param string $repositoryId the identifier for the repository
656
     * @param string $path the path to the object
657
     * @param string|null $filter a comma-separated list of query names that defines which properties must be
658
     *      returned by the repository (default is repository specific)
659
     * @param boolean $includeAllowableActions if <code>true</code>, then the repository must return the allowable
660
     *      actions for the object (default is <code>false</code>)
661
     * @param IncludeRelationships|null $includeRelationships indicates what relationships in which the objects
662
     *      participate must be returned (default is <code>IncludeRelationships::NONE</code>)
663
     * @param string $renditionFilter indicates what set of renditions the repository must return whose kind
664
     *      matches this filter (default is "cmis:none")
665
     * @param boolean $includePolicyIds if <code>true</code>, then the repository must return the policy ids for
666
     *      the object (default is <code>false</code>)
667
     * @param boolean $includeAcl if <code>true</code>, then the repository must return the ACL for the object
668
     *      (default is <code>false</code>)
669
     * @param ExtensionDataInterface|null $extension
670
     * @return ObjectDataInterface|null Returns object of type <code>ObjectDataInterface</code> or <code>null</code>
671
     *      if the repository response was empty
672
     */
673 3 View Code Duplication
    public function getObjectByPath(
674
        $repositoryId,
675
        $path,
676
        $filter = null,
677
        $includeAllowableActions = false,
678
        IncludeRelationships $includeRelationships = null,
679
        $renditionFilter = Constants::RENDITION_NONE,
680
        $includePolicyIds = false,
681
        $includeAcl = false,
682
        ExtensionDataInterface $extension = null
683
    ) {
684 3
        $url = $this->getPathUrl($repositoryId, $path, Constants::SELECTOR_OBJECT);
685 3
        $url->getQuery()->modify(
686
            array(
687 3
                Constants::PARAM_ALLOWABLE_ACTIONS => $includeAllowableActions ? 'true' : 'false',
688 3
                Constants::PARAM_RENDITION_FILTER => $renditionFilter,
689 3
                Constants::PARAM_POLICY_IDS => $includePolicyIds ? 'true' : 'false',
690 3
                Constants::PARAM_ACL => $includeAcl ? 'true' : 'false',
691 3
                Constants::PARAM_SUCCINCT => $this->getSuccinct() ? 'true' : 'false',
692 3
                Constants::PARAM_DATETIME_FORMAT => (string) $this->getDateTimeFormat()
693 3
            )
694 3
        );
695
696 3
        if (!empty($filter)) {
697 2
            $url->getQuery()->modify(array(Constants::PARAM_FILTER => (string) $filter));
698 2
        }
699
700 3
        if ($includeRelationships !== null) {
701 2
            $url->getQuery()->modify(array(Constants::PARAM_RELATIONSHIPS => (string) $includeRelationships));
702 2
        }
703
704 3
        $responseData = $this->read($url)->json();
705
706
        // TODO Implement Cache
707 3
        return $this->getJsonConverter()->convertObject($responseData);
708
    }
709
710
    /**
711
     * Gets the list of properties for an object.
712
     *
713
     * @param string $repositoryId the identifier for the repository
714
     * @param string $objectId the identifier for the object
715
     * @param string|null $filter a comma-separated list of query names that defines which properties must be
716
     *      returned by the repository (default is repository specific)
717
     * @param ExtensionDataInterface|null $extension
718
     * @return PropertiesInterface
719
     */
720 2
    public function getProperties(
721
        $repositoryId,
722
        $objectId,
723
        $filter = null,
724
        ExtensionDataInterface $extension = null
725
    ) {
726 2
        $url = $this->getObjectUrl($repositoryId, $objectId, Constants::SELECTOR_PROPERTIES);
727 2
        $url->getQuery()->modify(
728
            array(
729 2
                Constants::PARAM_SUCCINCT => $this->getSuccinct() ? 'true' : 'false',
730 2
                Constants::PARAM_DATETIME_FORMAT => (string) $this->getDateTimeFormat()
731 2
            )
732 2
        );
733
734 2
        if (!empty($filter)) {
735 1
            $url->getQuery()->modify(array(Constants::PARAM_FILTER => (string) $filter));
736 1
        }
737
738 2
        $responseData = $this->read($url)->json();
739
740
        // TODO: Implement Cache
741 2
        if ($this->getSuccinct()) {
742
            return $this->getJsonConverter()->convertSuccinctProperties($responseData);
743
        } else {
744 2
            return $this->getJsonConverter()->convertProperties($responseData);
745
        }
746
    }
747
748
    /**
749
     * Gets the list of associated renditions for the specified object.
750
     * Only rendition attributes are returned, not rendition stream.
751
     *
752
     * @param string $repositoryId the identifier for the repository
753
     * @param string $objectId the identifier for the object
754
     * @param string $renditionFilter indicates what set of renditions the repository must return whose kind
755
     *      matches this filter (default is "cmis:none")
756
     * @param integer|null $maxItems the maximum number of items to return in a response
757
     *       (default is repository specific)
758
     * @param integer $skipCount number of potential results that the repository MUST skip/page over before
759
     *      returning any results (default is 0)
760
     * @param ExtensionDataInterface|null $extension
761
     * @return RenditionDataInterface[]
762
     * @throws CmisInvalidArgumentException If object id is empty or skip count not of type integer
763
     */
764 2
    public function getRenditions(
765
        $repositoryId,
766
        $objectId,
767
        $renditionFilter = Constants::RENDITION_NONE,
768
        $maxItems = null,
769
        $skipCount = 0,
770
        ExtensionDataInterface $extension = null
771
    ) {
772 2
        if (empty($objectId)) {
773
            throw new CmisInvalidArgumentException('Object id must not be empty!');
774
        }
775
776 2
        if (!is_int($skipCount)) {
777
            throw new CmisInvalidArgumentException('Skip count must be of type integer!');
778
        }
779
780 2
        $url = $this->getObjectUrl($repositoryId, $objectId, Constants::SELECTOR_RENDITIONS);
781 2
        $url->getQuery()->modify(
782
            array(
783 2
                Constants::PARAM_RENDITION_FILTER => $renditionFilter,
784 2
                Constants::PARAM_SKIP_COUNT => (string) $skipCount,
785
            )
786 2
        );
787
788 2
        if ($maxItems !== null) {
789 1
            $url->getQuery()->modify(array(Constants::PARAM_MAX_ITEMS => (string) $maxItems));
790 1
        }
791
792 2
        $responseData = $this->read($url)->json();
793
794 2
        return $this->getJsonConverter()->convertRenditions($responseData);
795
    }
796
797
    /**
798
     * Moves the specified file-able object from one folder to another.
799
     *
800
     * @param string $repositoryId the identifier for the repository
801
     * @param string $objectId the identifier for the object. The repository might return a different/new object id
802
     * @param string $targetFolderId the identifier for the target folder
803
     * @param string $sourceFolderId the identifier for the source folder
804
     * @param ExtensionDataInterface|null $extension
805
     * @return ObjectDataInterface|null Returns object of type ObjectDataInterface or <code>null</code>
806
     *     if the repository response was empty
807
     */
808 1
    public function moveObject(
809
        $repositoryId,
810
        & $objectId,
811
        $targetFolderId,
812
        $sourceFolderId,
813
        ExtensionDataInterface $extension = null
814
    ) {
815 1
        $url = $this->getObjectUrl($repositoryId, $objectId);
816 1
        $url->getQuery()->modify(
817
            array(
818 1
                Constants::CONTROL_CMISACTION => Constants::CMISACTION_MOVE,
819 1
                Constants::PARAM_TARGET_FOLDER_ID => $targetFolderId,
820 1
                Constants::PARAM_SOURCE_FOLDER_ID => $sourceFolderId,
821 1
                Constants::PARAM_SUCCINCT => $this->getSuccinct() ? 'true' : 'false'
822 1
            )
823 1
        );
824
825 1
        $responseData = $this->post($url)->json();
826 1
        $newObject = $this->getJsonConverter()->convertObject($responseData);
827
828
        // $objectId was passed by reference. The value is changed here to new object id
829 1
        $objectId = ($newObject === null) ? null : $newObject->getId();
830
831 1
        return $newObject;
832
    }
833
834
    /**
835
     * Sets the content stream for the specified document object.
836
     *
837
     * @param string $repositoryId The identifier for the repository
838
     * @param string $objectId The identifier for the object. The repository might return a different/new object id
839
     * @param StreamInterface $contentStream The content stream
840
     * @param boolean $overwriteFlag If <code>true</code>, then the repository must replace the existing content stream
841
     *      for the object (if any) with the input content stream. If <code>false</code>, then the repository must
842
     *      only set the input content stream for the object if the object currently does not have a content stream
843
     *      (default is <code>true</code>)
844
     * @param string|null $changeToken The last change token of this object that the client received.
845
     *      The repository might return a new change token (default is <code>null</code>)
846
     * @param ExtensionDataInterface|null $extension
847
     * @throws CmisInvalidArgumentException If object id is empty
848
     */
849 3
    public function setContentStream(
850
        $repositoryId,
851
        & $objectId,
852
        StreamInterface $contentStream,
853
        $overwriteFlag = true,
854
        & $changeToken = null,
855
        ExtensionDataInterface $extension = null
856
    ) {
857 3
        if (empty($objectId)) {
858
            throw new CmisInvalidArgumentException('Object id must not be empty!');
859
        }
860
861 3
        $url = $this->getObjectUrl($repositoryId, $objectId);
862
863 3
        $url->getQuery()->modify(
864
            array(
865 3
                Constants::CONTROL_CMISACTION => Constants::CMISACTION_SET_CONTENT,
866 3
                Constants::PARAM_OVERWRITE_FLAG => $overwriteFlag ? 'true' : 'false',
867 3
                Constants::PARAM_SUCCINCT => $this->getSuccinct() ? 'true' : 'false'
868 3
            )
869 3
        );
870
871 3 View Code Duplication
        if ($changeToken !== null && !$this->getSession()->get(SessionParameter::OMIT_CHANGE_TOKENS, false)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
872 1
            $url->getQuery()->modify(array(Constants::PARAM_CHANGE_TOKEN => $changeToken));
873 1
        }
874
875 3
        $responseData = $this->post(
876 3
            $url,
877
            $contentStream
878 3
        )->json();
879
880 3
        $newObject = $this->getJsonConverter()->convertObject($responseData);
881
882
        // $objectId was passed by reference. The value is changed here to new object id
883 3
        $objectId = null;
884 3 View Code Duplication
        if ($newObject !== null) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
885 3
            $objectId = $newObject->getId();
886 3
            $newObjectProperties = $newObject->getProperties()->getProperties();
887 3
            if ($changeToken !== null && count($newObjectProperties) > 0) {
888 2
                $newChangeToken = $newObjectProperties[PropertyIds::CHANGE_TOKEN];
889
                // $changeToken was passed by reference. The value is changed here
890 2
                $changeToken = $newChangeToken === null ? null : $newChangeToken->getFirstValue();
891 2
            }
892 3
        }
893 3
    }
894
895
    /**
896
     * Updates properties of the specified object.
897
     *
898
     * @param string $repositoryId The identifier for the repository
899
     * @param string $objectId The identifier for the object. The repository might return a different/new object id
900
     * @param PropertiesInterface $properties The updated property values that must be applied to the object
901
     * @param string|null $changeToken The last change token of this object that the client received.
902
     *      The repository might return a new change token (default is <code>null</code>)
903
     * @param ExtensionDataInterface|null $extension
904
     * @throws CmisInvalidArgumentException If $objectId is empty
905
     */
906 3
    public function updateProperties(
907
        $repositoryId,
908
        & $objectId,
909
        PropertiesInterface $properties,
910
        & $changeToken = null,
911
        ExtensionDataInterface $extension = null
912
    ) {
913 3
        if (empty($objectId)) {
914
            throw new CmisInvalidArgumentException('Object id must not be empty!');
915
        }
916
917 3
        $url = $this->getObjectUrl($repositoryId, $objectId);
918
919 3 View Code Duplication
        if ($changeToken !== null && !$this->getSession()->get(SessionParameter::OMIT_CHANGE_TOKENS, false)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
920 1
            $url->getQuery()->modify(array(Constants::PARAM_CHANGE_TOKEN => $changeToken));
921 1
        }
922
923 3
        $queryArray = $this->convertPropertiesToQueryArray($properties);
924 3
        $queryArray[Constants::CONTROL_CMISACTION] = Constants::CMISACTION_UPDATE_PROPERTIES;
925 3
        $queryArray[Constants::PARAM_SUCCINCT] = $this->getSuccinct() ? 'true' : 'false';
926 3
        $responseData = $this->post($url, $queryArray)->json();
927 3
        $newObject = $this->getJsonConverter()->convertObject($responseData);
928
929
        // $objectId was passed by reference. The value is changed here to new object id
930 3
        $objectId = null;
931 3 View Code Duplication
        if ($newObject !== null) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
932 3
            $objectId = $newObject->getId();
933 3
            $newObjectProperties = $newObject->getProperties()->getProperties();
934 3
            if ($changeToken !== null && count($newObjectProperties) > 0) {
935 2
                $newChangeToken = $newObjectProperties[PropertyIds::CHANGE_TOKEN];
936
                // $changeToken was passed by reference. The value is changed here
937 2
                $changeToken = $newChangeToken === null ? null : $newChangeToken->getFirstValue();
938 2
            }
939 3
        }
940 3
    }
941
}
942