Completed
Pull Request — develop (#481)
by
unknown
72:24 queued 66:11
created

testRecordOriginHandlingWithNoIdInPayload()   B

Complexity

Conditions 1
Paths 1

Size

Total Lines 24
Code Lines 15

Duplication

Lines 0
Ratio 0 %

Importance

Changes 3
Bugs 0 Features 1
Metric Value
c 3
b 0
f 1
dl 0
loc 24
rs 8.9713
cc 1
eloc 15
nc 1
nop 0
1
<?php
2
/**
3
 * test for RecordOriginConstraint
4
 */
5
6
namespace Graviton\SchemaBundle\Tests\ConstraintBuilder;
7
8
use Graviton\TestBundle\Test\RestTestCase;
9
use Symfony\Component\HttpFoundation\Response;
10
11
/**
12
 * @author   List of contributors <https://github.com/libgraviton/graviton/graphs/contributors>
13
 * @license  http://opensource.org/licenses/gpl-license.php GNU Public License
14
 * @link     http://swisscom.ch
15
 */
16
class RecordOriginConstraintTest extends RestTestCase
17
{
18
19
    /**
20
     * load fixtures
21
     *
22
     * @return void
23
     */
24
    public function setUp()
25
    {
26
        $this->loadFixtures(
27
            array(
28
                'GravitonDyn\CustomerBundle\DataFixtures\MongoDB\LoadCustomerData',
29
            ),
30
            null,
31
            'doctrine_mongodb'
32
        );
33
    }
34
35
    /**
36
     * test the validation of the RecordOriginConstraint
37
     *
38
     * @dataProvider createDataProvider
39
     *
40
     * @param object  $entity           The object to create
41
     * @param integer $expectedStatus   Header status code
42
     * @param string  $expectedResponse Post data result of post
43
     *
44
     * @return void
45
     */
46 View Code Duplication
    public function testRecordOriginHandlingOnCreate($entity, $expectedStatus, $expectedResponse)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in 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...
47
    {
48
        $client = static::createRestClient();
49
        $client->post('/person/customer/', $entity);
50
51
        $response = $client->getResponse();
52
        $this->assertEquals($expectedStatus, $response->getStatusCode());
53
        $this->assertEquals($expectedResponse, $client->getResults());
54
    }
55
56
    /**
57
     * tests for the case if user doesn't provide an id in payload.. constraint
58
     * must take the id from the request in that case.
59
     *
60
     * @return void
61
     */
62
    public function testRecordOriginHandlingWithNoIdInPayload()
63
    {
64
        $record = (object) [
65
            //'id' => '' - no, no id.. that's the point ;-)
66
            'customerNumber' => 555,
67
            'name' => 'Muster Hans'
68
        ];
69
70
        $client = static::createRestClient();
71
        $client->put('/person/customer/100', $record);
72
73
        $this->assertEquals(
74
            (object) [
75
                'propertyPath' => 'recordOrigin',
76
                'message' => 'Prohibited modification attempt on record with recordOrigin of core.'
77
                    .' You tried to change (customerNumber, name, someObject), but You can only change'
78
                    .' by recordCoreException: (addedField, someObject.twoField).'
79
            ],
80
            $client->getResults()[0]
81
        );
82
83
        $this->assertEquals(1, count($client->getResults()));
84
        $this->assertEquals(Response::HTTP_BAD_REQUEST, $client->getResponse()->getStatusCode());
85
    }
86
87
    /**
88
     * Test the validation of the RecordOriginConstraint
89
     *
90
     * @param array   $fieldsToSet      Fields to be modified
91
     * @param integer $expectedStatus   Header status code
92
     * @param string  $expectedResponse Result to be returned
93
     * @param boolean $checkSavedEntry  To check db for correct result
94
     *
95
     * @dataProvider updateDataProvider
96
     *
97
     * @return void
98
     */
99
    public function testRecordOriginHandlingOnUpdate(
100
        $fieldsToSet,
101
        $expectedStatus,
102
        $expectedResponse,
103
        $checkSavedEntry = true
104
    ) {
105
        $client = static::createRestClient();
106
        $client->request('GET', '/person/customer/100');
107
        $result = $client->getResults();
108
109
        // apply changes
110
        foreach ($fieldsToSet as $key => $val) {
111
            $result->{$key} = $val;
112
        }
113
114
        $expectedObject = $result;
115
116
        $client = static::createRestClient();
117
        $client->put('/person/customer/100', $result);
118
119
        $response = $client->getResponse();
120
        $this->assertEquals($expectedStatus, $response->getStatusCode());
121
        $this->assertEquals($expectedResponse, $client->getResults());
122
123
        if ($checkSavedEntry) {
124
            // fetch it again and compare
125
            $client = static::createRestClient();
126
            $client->request('GET', '/person/customer/100');
127
            $this->assertEquals($expectedObject, $client->getResults());
128
        }
129
    }
130
131
    /**
132
     * Test the validation of the RecordOriginConstraint
133
     *
134
     * @param array   $ops              PATCH operations
135
     * @param integer $expectedStatus   Header status code
136
     * @param string  $expectedResponse Result to be returned
137
     *
138
     * @dataProvider patchDataProvider
139
     *
140
     * @return void
141
     */
142 View Code Duplication
    public function testRecordOriginHandlingOnPatch(
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in 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...
143
        $ops,
144
        $expectedStatus,
145
        $expectedResponse
146
    ) {
147
        $client = static::createRestClient();
148
149
        $client->request('PATCH', '/person/customer/100', [], [], [], json_encode($ops));
150
151
        $response = $client->getResponse();
152
        $this->assertEquals($expectedStatus, $response->getStatusCode());
153
        $this->assertEquals($expectedResponse, $client->getResults());
154
    }
155
156
    /**
157
     * test to see if DELETE on a recordorigin: core is denied
158
     *
159
     * @return void
160
     */
161
    public function testDeleteHandling()
162
    {
163
        $client = static::createRestClient();
164
        $client->request('DELETE', '/person/customer/100');
165
        $response = $client->getResponse();
166
167
        $this->assertEquals(Response::HTTP_BAD_REQUEST, $response->getStatusCode());
168
        $this->assertEquals(
169
            (object) [
170
                'propertyPath' => 'recordOrigin',
171
                'message' => 'Must not be one of the following keywords: core'
172
            ],
173
            $client->getResults()
174
        );
175
    }
176
177
    /**
178
     * Data provider for POST related stuff
179
     *
180
     * @return array
0 ignored issues
show
Documentation introduced by
Consider making the return type a bit more specific; maybe use array<string,array<string,null|array>>.

This check looks for the generic type array as a return type and suggests a more specific type. This type is inferred from the actual code.

Loading history...
181
     */
182
    public function createDataProvider()
183
    {
184
        $baseObj = [
185
            'customerNumber' => 888,
186
            'name' => 'Muster Hans'
187
        ];
188
189
        return [
190
191
            /*** STUFF THAT SHOULD BE ALLOWED ***/
192
193
            'create-allowed-object' => [
194
                'entity' => (object) array_merge(
195
                    $baseObj,
196
                    [
197
                        'recordOrigin' => 'hans'
198
                    ]
199
                ),
200
                'httpStatusExpected' => Response::HTTP_CREATED,
201
                'expectedResponse' => null
202
            ],
203
204
            /*** STUFF THAT SHOULD BE DENIED ***/
205
206
            'create-recordorigin-core' => [
207
                'entity' => (object) array_merge(
208
                    $baseObj,
209
                    [
210
                        'recordOrigin' => 'core'
211
                    ]
212
                ),
213
                'httpStatusExpected' => Response::HTTP_BAD_REQUEST,
214
                'expectedResponse' => [
215
                    (object) [
216
                        'propertyPath' => 'recordOrigin',
217
                        'message' => 'Creating documents with the recordOrigin field having a '.
218
                            'value of core is not permitted.'
219
                    ]
220
                ]
221
            ]
222
        ];
223
    }
224
225
    /**
226
     * Data provider for PUT related stuff
227
     *
228
     * @return array
0 ignored issues
show
Documentation introduced by
Consider making the return type a bit more specific; maybe use array<string,array>.

This check looks for the generic type array as a return type and suggests a more specific type. This type is inferred from the actual code.

Loading history...
229
     */
230
    public function updateDataProvider()
231
    {
232
        return [
233
234
            /*** STUFF THAT SHOULD BE ALLOWED ***/
235
            'create-allowed-object' => [
236
                'fieldsToSet' => [
237
                    'addedField' => (object) [
238
                        'some' => 'property',
239
                        'another' => 'one'
240
                    ]
241
                ],
242
                'httpStatusExpected' => Response::HTTP_NO_CONTENT,
243
                'expectedResponse' => null
244
            ],
245
            'subproperty-modification' => [
246
                'fieldsToSet' => [
247
                    'someObject' => (object) [
248
                        'oneField' => 'value',
249
                        'twoField' => 'twofield'
250
                    ]
251
                ],
252
                'httpStatusExpected' => Response::HTTP_NO_CONTENT,
253
                'expectedResponse' => null
254
            ],
255
256
            /*** STUFF THAT NEEDS TO BE DENIED ***/
257
            'denied-subproperty-modification' => [
258
                'fieldsToSet' => [
259
                    'someObject' => (object) [
260
                        'oneField' => 'changed-value'
261
                    ]
262
                ],
263
                'httpStatusExpected' => Response::HTTP_BAD_REQUEST,
264
                'expectedResponse' => $this->getExpectedErrorMessage('someObject'),
265
                'checkSavedEntry' => false
266
            ],
267
            'denied-try-change-recordorigin' => [
268
                'fieldsToSet' => [
269
                    'recordOrigin' => 'hans'
270
                ],
271
                'httpStatusExpected' => Response::HTTP_BAD_REQUEST,
272
                'expectedResponse' => $this->getExpectedErrorMessage('recordOrigin'),
273
                'checkSavedEntry' => false
274
            ],
275
        ];
276
    }
277
278
279
    /**
280
     * providing the conditional errorMessage Object
281
     *
282
     * @param string $changedFields the Field the user wants to change
283
     *
284
     * @return array
285
     */
286
    private function getExpectedErrorMessage($changedFields)
287
    {
288
        $expectedErrorOutput = [
289
            (object) [
290
                'propertyPath' => 'recordOrigin',
291
                'message' => 'Prohibited modification attempt on record with recordOrigin of core.'
292
                    .' You tried to change ('.$changedFields.'), but You can only change'
293
                    .' by recordCoreException: (addedField, someObject.twoField).'
294
            ]
295
        ];
296
        return $expectedErrorOutput;
297
    }
298
299
    /**
300
     * Data provider for PATCH related stuff
301
     *
302
     * @return array
0 ignored issues
show
Documentation introduced by
Consider making the return type a bit more specific; maybe use array<string,array>.

This check looks for the generic type array as a return type and suggests a more specific type. This type is inferred from the actual code.

Loading history...
303
     */
304
    public function patchDataProvider()
305
    {
306
        return [
307
308
            /*** STUFF THAT SHOULD BE ALLOWED ***/
309
310
            'patch-allowed-attribute' => [
311
                'ops' => [
312
                    [
313
                        'op' => 'add',
314
                        'path' => '/someObject/twoField',
315
                        'value' => 'myValue'
316
                    ]
317
                ],
318
                'httpStatusExpected' => Response::HTTP_OK,
319
                'expectedResponse' => null
320
            ],
321
            'patch-add-object-data' => [
322
                'ops' => [
323
                    [
324
                        'op' => 'add',
325
                        'path' => '/addedField',
326
                        'value' => [
327
                            'someProperty' => 'someValue',
328
                            'anotherOne' => 'oneMore'
329
                        ]
330
                    ]
331
                ],
332
                'httpStatusExpected' => Response::HTTP_OK,
333
                'expectedResponse' => null
334
            ],
335
336
            /*** STUFF THAT NEEDS TO BE DENIED ***/
337
            'patch-denied-subproperty' => [
338
                'ops' => [
339
                    [
340
                        'op' => 'add',
341
                        'path' => '/someObject/oneField',
342
                        'value' => 'myValue'
343
                    ]
344
                ],
345
                'httpStatusExpected' => Response::HTTP_BAD_REQUEST,
346
                'expectedResponse' => $this->getExpectedErrorMessage('someObject')
347
            ],
348
            'patch-denied-recordorigin-change' => [
349
                'ops' => [
350
                    [
351
                        'op' => 'replace',
352
                        'path' => '/recordOrigin',
353
                        'value' => 'hans'
354
                    ]
355
                ],
356
                'httpStatusExpected' => Response::HTTP_BAD_REQUEST,
357
                'expectedResponse' => $this->getExpectedErrorMessage('recordOrigin')
358
            ],
359
360
        ];
361
    }
362
}
363