Completed
Push — ezp26297-rest_embedding_http_c... ( 745663...9be4a0 )
by
unknown
22:44
created

ContentTest::testDeleteContent()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 9
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 5
nc 1
nop 1
dl 0
loc 9
rs 9.6666
c 0
b 0
f 0
1
<?php
2
3
/**
4
 * File containing the Functional\ContentTest class.
5
 *
6
 * @copyright Copyright (C) eZ Systems AS. All rights reserved.
7
 * @license For full copyright and license information view LICENSE file distributed with this source code.
8
 *
9
 * @version //autogentag//
10
 */
11
namespace eZ\Bundle\EzPublishRestBundle\Tests\Functional;
12
13
use Buzz\Message\Response;
14
use eZ\Bundle\EzPublishRestBundle\Tests\Functional\TestCase as RESTFunctionalTestCase;
15
16
class ContentTest extends RESTFunctionalTestCase
17
{
18
    private $createdContentTypeId = 1;
19
20
    /**
21
     * @covers POST /content/objects
22
     *
23
     * @return string REST content ID
24
     */
25 View Code Duplication
    public function testCreateContent()
26
    {
27
        $request = $this->createHttpRequest('POST', '/api/ezp/v2/content/objects', 'ContentCreate+xml', 'ContentInfo+json');
28
        $string = $this->addTestSuffix(__FUNCTION__);
29
        $body = <<< XML
30
<?xml version="1.0" encoding="UTF-8"?>
31
<ContentCreate>
32
  <ContentType href="/api/ezp/v2/content/types/{$this->createdContentTypeId}" />
33
  <mainLanguageCode>eng-GB</mainLanguageCode>
34
  <LocationCreate>
35
    <ParentLocation href="/api/ezp/v2/content/locations/1/2" />
36
    <priority>0</priority>
37
    <hidden>false</hidden>
38
    <sortField>PATH</sortField>
39
    <sortOrder>ASC</sortOrder>
40
  </LocationCreate>
41
  <Section href="/api/ezp/v2/content/sections/1" />
42
  <alwaysAvailable>true</alwaysAvailable>
43
  <remoteId>{$string}</remoteId>
44
  <User href="/api/ezp/v2/user/users/14" />
45
  <modificationDate>2012-09-30T12:30:00</modificationDate>
46
  <fields>
47
    <field>
48
      <fieldDefinitionIdentifier>name</fieldDefinitionIdentifier>
49
      <languageCode>eng-GB</languageCode>
50
      <fieldValue>{$string}</fieldValue>
51
    </field>
52
  </fields>
53
</ContentCreate>
54
XML;
55
        $request->setContent($body);
56
57
        $response = $this->sendHttpRequest($request);
58
59
        self::assertHttpResponseCodeEquals($response, 201);
60
        self::assertHttpResponseHasHeader($response, 'Location');
61
62
        $href = $response->getHeader('Location');
63
        $this->addCreatedElement($href);
64
65
        return $href;
66
    }
67
68
    /**
69
     * @depends testCreateContent
70
     * @covers PUBLISH /content/objects/<contentId>/versions/<versionNumber>
71
     *
72
     * @return string REST content ID
73
     */
74
    public function testPublishContent($restContentHref)
75
    {
76
        $response = $this->sendHttpRequest(
77
            $this->createHttpRequest('PUBLISH', "$restContentHref/versions/1")
78
        );
79
        self::assertHttpResponseCodeEquals($response, 204);
80
81
        return $restContentHref;
82
    }
83
84
    /**
85
     * @depends testPublishContent
86
     * @covers GET /content/objects?remoteId=<remoteId>
87
     */
88
    public function testRedirectContent($restContentHref)
89
    {
90
        $response = $this->sendHttpRequest(
91
            $this->createHttpRequest('GET', '/api/ezp/v2/content/objects?remoteId=' . $this->addTestSuffix('testCreateContent'))
92
        );
93
94
        self::assertHttpResponseCodeEquals($response, 307);
95
        self::assertEquals($response->getHeader('Location'), $restContentHref);
96
    }
97
98
    /**
99
     * @depends testPublishContent
100
     */
101 View Code Duplication
    public function testLoadContent($restContentHref)
102
    {
103
        $response = $this->sendHttpRequest(
104
            $this->createHttpRequest('GET', $restContentHref, '', 'ContentInfo+json')
105
        );
106
107
        self::assertHttpResponseCodeEquals($response, 200);
108
109
        return $response;
110
    }
111
112
    /**
113
     * @depends testLoadContent
114
     */
115
    public function testLoadContentCacheTags(Response $response)
116
    {
117
        $responseStruct = json_decode($response->getContent(), true);
118
119
        $this->assertHttpResponseHasCacheTags(
120
            $response,
121
            [
122
                'location-' . $this->extractLastIdFromHref($responseStruct['Content']['MainLocation']['_href']),
123
                'content-' . $responseStruct['Content']['_id'],
124
                'content-type-' . $this->extractLastIdFromHref($responseStruct['Content']['ContentType']['_href'])
125
            ]
126
        );
127
    }
128
129
    /**
130
     * @depends testPublishContent
131
     */
132
    public function testUpdateContentMetadata($restContentHref)
133
    {
134
        $string = $this->addTestSuffix(__FUNCTION__);
135
        $content = <<< XML
136
<?xml version="1.0" encoding="UTF-8"?>
137
<ContentUpdate>
138
  <Owner href="/api/ezp/v2/user/users/10"/>
139
  <remoteId>{$string}</remoteId>
140
</ContentUpdate>
141
XML;
142
        $request = $this->createHttpRequest('PATCH', $restContentHref, 'ContentUpdate+xml', 'ContentInfo+json');
143
        $request->setContent($content);
144
        $response = $this->sendHttpRequest($request);
145
        self::assertHttpResponseCodeEquals($response, 200);
146
147
        // @todo test data
148
    }
149
150
    /**
151
     * @depends testPublishContent
152
     *
153
     * @return string ContentVersion REST ID
154
     */
155 View Code Duplication
    public function testCreateDraftFromVersion($restContentHref)
156
    {
157
        $response = $this->sendHttpRequest(
158
            $this->createHttpRequest('COPY', "{$restContentHref}/versions/1")
159
        );
160
161
        self::assertHttpResponseCodeEquals($response, 201);
162
        self::assertEquals($response->getHeader('Location'), "{$restContentHref}/versions/2");
163
164
        return $response->getHeader('Location');
165
    }
166
167
    /**
168
     * @depends testPublishContent
169
     * @covers GET /content/objects/<contentId>/currentversion
170
     * @covers \eZ\Publish\Core\REST\Server\Controller\Content::redirectCurrentVersion
171
     */
172 View Code Duplication
    public function testRedirectCurrentVersion($restContentHref)
173
    {
174
        $response = $this->sendHttpRequest(
175
            $this->createHttpRequest('GET', "$restContentHref/currentversion")
176
        );
177
178
        self::assertHttpResponseCodeEquals($response, 307);
179
        self::assertHttpResponseHasHeader($response, 'Location', "$restContentHref/versions/1");
180
181
        $this->assertHttpResponseHasCacheTags(
182
            $response,
183
            [
184
                'content-' . $this->extractLastIdFromHref($restContentHref)
185
            ]
186
        );
187
    }
188
189
    /**
190
     * @depends testCreateDraftFromVersion
191
     * @covers GET /content/objects/<contentId>/versions/<versionNumber>
192
     *
193
     * @param string $restContentVersionHref
194
     */
195 View Code Duplication
    public function testLoadContentVersion($restContentVersionHref)
196
    {
197
        $response = $this->sendHttpRequest(
198
            $this->createHttpRequest('GET', $restContentVersionHref, '', 'Version+json')
199
        );
200
201
        self::assertHttpResponseCodeEquals($response, 200);
202
        // @todo test data
203
        // @todo test filtering (language, fields, etc)
204
205
        return $response;
206
    }
207
208
    /**
209
     * @depends testLoadContentVersion
210
     */
211
    public function testLoadContentVersionCacheTags(Response $response)
212
    {
213
        $responseStruct = json_decode($response->getContent(), true);
214
215
        $this->assertHttpResponseHasCacheTags(
216
            $response,
217
            [
218
                'content-' . $this->extractLastIdFromHref(
219
                    $responseStruct['Version']['VersionInfo']['Content']['_href']
220
                ),
221
                'content-type-' . $this->createdContentTypeId
222
            ]
223
        );
224
    }
225
226
    /**
227
     * @covers COPY /content/objects/<contentId>
228
     * @depends testPublishContent
229
     *
230
     * @return string the copied content href
231
     */
232
    public function testCopyContent($restContentHref)
233
    {
234
        $testContent = $this->loadContent($restContentHref);
235
236
        $request = $this->createHttpRequest('COPY', $restContentHref);
237
        $request->addHeader('Destination: ' . $testContent['MainLocation']['_href']);
238
239
        $response = $this->sendHttpRequest($request);
240
241
        self::assertHttpResponseCodeEquals($response, 201);
242
        self::assertStringStartsWith('/api/ezp/v2/content/objects/', $response->getHeader('Location'));
243
244
        $this->addCreatedElement($response->getHeader('Location'));
245
246
        return $response->getHeader('Location');
247
    }
248
249
    /**
250
     * @covers DELETE /content/objects/<versionNumber>
251
     * @depends testCopyContent
252
     */
253
    public function testDeleteContent($restContentHref)
254
    {
255
        self::markTestSkipped("Fails as the content created by copyContent isn't found");
256
        $response = $this->sendHttpRequest(
257
            $this->createHttpRequest('DELETE', $restContentHref)
258
        );
259
260
        self::assertHttpResponseCodeEquals($response, 204);
261
    }
262
263
    /**
264
     * @depends testPublishContent
265
     * @covers GET /content/objects/<contentId>/versions
266
     */
267
    public function testLoadContentVersions($restContentHref)
268
    {
269
        $response = $this->sendHttpRequest(
270
            $this->createHttpRequest('GET', "$restContentHref/versions", '', 'VersionList')
271
        );
272
273
        self::assertHttpResponseCodeEquals($response, 200);
274
    }
275
276
    /**
277
     * @depends testPublishContent
278
     *
279
     * @param string $restContentHref /content/objects/<contentId>
280
     * @covers COPY /content/objects/<contentId>/currentversion
281
     *
282
     * @return string the ID of the created version (/content/objects/<contentId>/versions/<versionNumber>
283
     */
284 View Code Duplication
    public function testCreateDraftFromCurrentVersion($restContentHref)
285
    {
286
        $response = $this->sendHttpRequest(
287
            $this->createHttpRequest('COPY', "$restContentHref/currentversion")
288
        );
289
290
        self::assertHttpResponseCodeEquals($response, 201);
291
        self::assertHttpResponseHasHeader($response, 'Location');
292
293
        return $response->getHeader('Location');
294
    }
295
296
    /**
297
     * @depends testCreateDraftFromCurrentVersion
298
     *
299
     * @param string $restContentVersionHref /api/ezp/v2/content/objects/<contentId>/versions>/<versionNumber>
300
     * @covers DELETE /api/ezp/v2/content/objects/<contentId>/versions>/<versionNumber>
301
     */
302
    public function testDeleteContentVersion($restContentVersionHref)
303
    {
304
        $response = $this->sendHttpRequest(
305
            $this->createHttpRequest('DELETE', $restContentVersionHref)
306
        );
307
308
        self::assertHttpResponseCodeEquals($response, 204);
309
    }
310
311
    /**
312
     * @depends testCreateDraftFromVersion
313
     * @covers PATCH /content/objects/<contentId>/versions>/<versionNumber>
314
     *
315
     * @param string $restContentVersionHref /content/objects/<contentId>/versions>/<versionNumber>
316
     */
317
    public function testUpdateVersion($restContentVersionHref)
318
    {
319
        $xml = <<< XML
320
<VersionUpdate>
321
    <fields>
322
        <field>
323
            <fieldDefinitionIdentifier>name</fieldDefinitionIdentifier>
324
            <languageCode>eng-GB</languageCode>
325
            <fieldValue>testUpdateVersion</fieldValue>
326
        </field>
327
    </fields>
328
</VersionUpdate>
329
XML;
330
331
        $request = $this->createHttpRequest('PATCH', $restContentVersionHref, 'VersionUpdate+xml', 'Version+json');
332
        $request->setContent($xml);
333
        $response = $this->sendHttpRequest(
334
            $request
335
        );
336
337
        self::assertHttpResponseCodeEquals($response, 200);
338
    }
339
340
    /**
341
     * @depends testPublishContent
342
     * @covers GET /content/objects/<contentId>/relations
343
     */
344
    public function testRedirectCurrentVersionRelations($restContentHref)
345
    {
346
        $response = $this->sendHttpRequest(
347
            $this->createHttpRequest('GET', "$restContentHref/relations")
348
        );
349
350
        self::assertHttpResponseCodeEquals($response, 307);
351
352
        // @todo Fix, see EZP-21059. Meanwhile, the test is skipped if it fails as expected
353
        // self::assertHttpResponseHasHeader( $response, 'Location', "$restContentHref/versions/1/relations" );
354
        self::assertHttpResponseHasHeader($response, 'Location', "$restContentHref/relations?versionNumber=1");
355
        self::markTestIncomplete('@todo Fix issue EZP-21059');
356
    }
357
358
    /**
359
     * @depends testCreateDraftFromVersion
360
     * @covers GET /content/objects/<contentId>/versions/<versionNumber>/relations
361
     */
362 View Code Duplication
    public function testLoadVersionRelations($restContentVersionHref)
363
    {
364
        $response = $this->sendHttpRequest(
365
            $this->createHttpRequest('GET', "$restContentVersionHref/relations")
366
        );
367
368
        self::assertHttpResponseCodeEquals($response, 200);
369
370
        $this->assertHttpResponseHasCacheTags(
371
            $response,
372
            [
373
                'content-' . $this->extractContentIdFromHref($restContentVersionHref)
374
            ]
375
        );
376
    }
377
378
    /**
379
     * @depends testCreateDraftFromVersion
380
     * @covers POST /content/objects/<contentId>/versions/<versionNumber>/relations/<relationId>
381
     *
382
     * @return string created relation HREF (/content/objects/<contentId>/versions/<versionNumber>/relations/<relationId>
383
     */
384
    public function testCreateRelation($restContentVersionHref)
385
    {
386
        $content = <<< XML
387
<?xml version="1.0" encoding="UTF-8"?>
388
<RelationCreate>
389
  <Destination href="/api/ezp/v2/content/objects/10"/>
390
</RelationCreate>
391
XML;
392
393
        $request = $this->createHttpRequest('POST', "$restContentVersionHref/relations", 'RelationCreate+xml', 'Relation+json');
394
        $request->setContent($content);
395
396
        $response = $this->sendHttpRequest($request);
397
398
        self::assertHttpResponseCodeEquals($response, 201);
399
400
        $response = json_decode($response->getContent(), true);
401
402
        return $response['Relation']['_href'];
403
    }
404
405
    /**
406
     * @depends testCreateRelation
407
     * @covers GET /content/objects/<contentId>/versions/<versionNo>/relations/<relationId>
408
     */
409
    public function testLoadVersionRelation($restContentRelationHref)
410
    {
411
        $response = $this->sendHttpRequest(
412
            $this->createHttpRequest('GET', $restContentRelationHref)
413
        );
414
415
        self::assertHttpResponseCodeEquals($response, 200);
416
417
        $this->assertHttpResponseHasCacheTags(
418
            $response,
419
            ['content-' . $this->extractContentIdFromHref($restContentRelationHref)]
420
        );
421
    }
422
423
    /**
424
     * Returns the Content key from the decoded JSON of $restContentId's contentInfo.
425
     *
426
     *
427
     * @throws \InvalidArgumentException
428
     *
429
     * @param string $restContentHref /api/ezp/v2/content/objects/<contentId>
430
     *
431
     * @return array
432
     */
433
    private function loadContent($restContentHref)
434
    {
435
        $response = $this->sendHttpRequest(
436
            $this->createHttpRequest('GET', $restContentHref, '', 'ContentInfo+json')
437
        );
438
439
        if ($response->getStatusCode() != 200) {
440
            throw new \InvalidArgumentException("Content with ID $restContentHref could not be loaded");
441
        }
442
443
        $array = json_decode($response->getContent(), true);
444
        if ($array === null) {
445
            self::fail('Error loading content. Response: ' . $response->getContent());
446
        }
447
448
        return $array['Content'];
449
    }
450
451
    public function testCreateView()
452
    {
453
        $body = <<< XML
454
<?xml version="1.0" encoding="UTF-8"?>
455
<ViewInput>
456
  <identifier>testCreateView</identifier>
457
  <Query>
458
    <Criteria>
459
      <ContentTypeIdentifierCriterion>folder</ContentTypeIdentifierCriterion>
460
    </Criteria>
461
    <limit>10</limit>
462
    <offset>0</offset>
463
  </Query>
464
</ViewInput>
465
XML;
466
        $request = $this->createHttpRequest('POST', '/api/ezp/v2/content/views', 'ViewInput+xml', 'View+json');
467
        $request->setContent($body);
468
        $response = $this->sendHttpRequest(
469
            $request
470
        );
471
472
        // Returns 301 since 6.0 (deprecated in favour of /views)
473
        self::assertHttpResponseCodeEquals($response, 301);
474
        self::assertHttpResponseHasHeader($response, 'Location');
475
    }
476
477
    /**
478
     * Asserts that $response has the given set of $cacheTags.
479
     *
480
     * @param Response $response
481
     * @param array $expectedTags Example: ['content-42', 'location-300']
482
     */
483
    private function assertHttpResponseHasCacheTags(Response $response, $expectedTags)
484
    {
485
        $this->assertHttpResponseHasHeader($response, 'xkey');
486
487
        $responseCacheTag = $response->getHeader('xkey');
488
        foreach ($expectedTags as $expectedTag) {
489
            $this->assertContains($expectedTag, $responseCacheTag);
490
        }
491
    }
492
493
    /**
494
     * Extracts and returns the last id from $href.
495
     *
496
     * @param string $href Ex: '/api/ezp/v2/content/objects/1'
497
     * @return int Ex: 1
498
     */
499
    protected function extractLastIdFromHref($href)
500
    {
501
        $contentTypeHrefParts = explode('/', $href);
502
503
        return (int)array_pop($contentTypeHrefParts);
504
    }
505
506
    private function extractPathFromHref($href)
507
    {
508
        $parts = array_filter(
509
            explode('/', str_replace('/api/ezp/v2/', '', $href)),
510
            function ($value) {
511
                return is_numeric($value);
512
            }
513
        );
514
515
        return $parts;
516
    }
517
518
    /**
519
     * Extracts a content id from any href containing one.
520
     *
521
     * @param string $href Ex: /api/ezp/v2/content/objects/1/anything
522
     * @return int
523
     */
524
    private function extractContentIdFromHref($href)
525
    {
526
        $contentId = null;
527
        $leftOvers = null;
528
529
        sscanf(
530
            $href,
531
            '/api/ezp/v2/content/objects/%d/%s',
532
            $contentId,
533
            $leftOvers
534
        );
535
536
        return $contentId;
537
    }
538
}
539