Passed
Push — feature/insert-ignore ( 4b1dfb )
by Mathieu
04:10
created

DBObjectTest::testDBProperty()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 23
Code Lines 17

Duplication

Lines 0
Ratio 0 %

Importance

Changes 3
Bugs 0 Features 0
Metric Value
cc 1
eloc 17
c 3
b 0
f 0
nc 1
nop 0
dl 0
loc 23
rs 9.7
1
<?php
2
require_once 'stubs/Category.php';
3
4
/**
5
 * @SuppressWarnings("StaticAccess")
6
 */
7
class DBObjectTest extends \PHPUnit\Framework\TestCase
8
{
9
    protected $tableName = 'users';
10
    public function testContructor()
11
    {
12
        $classname = '\Suricate\DBObject';
13
14
        // Get mock, without the constructor being called
15
        $mock = $this->getMockBuilder($classname)
16
            ->disableOriginalConstructor()
17
            ->setMethods(array('setRelations'))
18
            ->getMockForAbstractClass();
19
20
        // set expectations for constructor calls
21
        $mock->expects($this->once())->method('setRelations');
22
23
        // now call the constructor
24
        $reflectedClass = new ReflectionClass($classname);
25
        $constructor = $reflectedClass->getConstructor();
26
        $constructor->invoke($mock);
27
    }
28
29
    public function testGetTableName()
30
    {
31
        $testName = 'my_sql_table';
32
33
        $testDBO = new \Suricate\DBObject();
34
        self::mockProperty($testDBO, 'tableName', $testName);
35
        $this->assertEquals($testName, $testDBO->getTableName());
36
    }
37
38
    public function testStaticTableName()
39
    {
40
        $this->assertEquals('categories', Category::tableName());
41
    }
42
43
    public function testGetTableIndex()
44
    {
45
        $testIndex = 'id';
46
47
        $testDBO = new \Suricate\DBObject();
48
        self::mockProperty($testDBO, 'tableIndex', $testIndex);
49
        $this->assertEquals($testIndex, $testDBO->getTableIndex());
50
    }
51
52
    public function testStaticTableIndex()
53
    {
54
        $this->assertEquals('id', Category::tableIndex());
55
    }
56
57
    public function testGetDBConfig()
58
    {
59
        $testConfigName = 'my_config';
60
61
        $testDBO = new \Suricate\DBObject();
62
        self::mockProperty($testDBO, 'DBConfig', $testConfigName);
63
        $this->assertEquals($testConfigName, $testDBO->getDBConfig());
64
    }
65
66
    public function testUndefinedGet()
67
    {
68
        $testDBO = new \Suricate\DBObject();
69
        self::mockProperty($testDBO, 'dbVariables', [
70
            'id',
71
            'name',
72
            'last_update'
73
        ]);
74
        $this->expectException(\InvalidArgumentException::class);
75
76
        $testDBO->undefinedVar;
0 ignored issues
show
Bug Best Practice introduced by
The property undefinedVar does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
77
    }
78
79
    public function testDBProperty()
80
    {
81
        $testDBO = new \Suricate\DBObject();
82
        $testDBO->regularProperty = 42;
0 ignored issues
show
Bug Best Practice introduced by
The property regularProperty does not exist on Suricate\DBObject. Since you implemented __set, consider adding a @property annotation.
Loading history...
83
        self::mockProperty($testDBO, 'dbVariables', [
84
            'id',
85
            'name',
86
            'not_loaded_var'
87
        ]);
88
        self::mockProperty($testDBO, 'dbValues', [
89
            'id' => 1,
90
            'name' => 'test name'
91
        ]);
92
        $this->assertEquals($testDBO->id, 1);
0 ignored issues
show
Bug Best Practice introduced by
The property id does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
93
        $this->assertNotEquals($testDBO->name, 'test name edited');
0 ignored issues
show
Bug Best Practice introduced by
The property name does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
94
        $this->assertNull($testDBO->not_loaded_var);
0 ignored issues
show
Bug Best Practice introduced by
The property not_loaded_var does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
95
96
        $this->assertTrue($testDBO->isDBVariable('id'));
97
        $this->assertFalse($testDBO->isDBVariable('regularProperty'));
98
99
        $this->assertTrue($testDBO->propertyExists('regularProperty'));
100
        $this->assertTrue($testDBO->propertyExists('id'));
101
        $this->assertFalse($testDBO->propertyExists('unknownProperty'));
102
    }
103
104
    public function testIsset()
105
    {
106
        $testDBO = new \Suricate\DBObject();
107
        self::mockProperty($testDBO, 'dbVariables', [
108
            'id',
109
            'name',
110
            'not_loaded_var'
111
        ]);
112
        self::mockProperty($testDBO, 'dbValues', [
113
            'id' => 1,
114
            'name' => 'test name'
115
        ]);
116
117
        $this->assertTrue(isset($testDBO->id));
0 ignored issues
show
Bug Best Practice introduced by
The property id does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
118
        $this->assertFalse(isset($testDBO->undefVar));
0 ignored issues
show
Bug Best Practice introduced by
The property undefVar does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
119
    }
120
121
    public function testIsLoaded()
122
    {
123
        $testIndex = 'id';
124
125
        $testDBO = new \Suricate\DBObject();
126
        self::mockProperty($testDBO, 'tableIndex', $testIndex);
127
        self::mockProperty($testDBO, 'dbVariables', [
128
            $testIndex,
129
            'name',
130
            'not_loaded_var'
131
        ]);
132
        $this->assertFalse($testDBO->isLoaded());
133
134
        self::mockProperty($testDBO, 'dbValues', [
135
            $testIndex => 1,
136
            'name' => 'test name'
137
        ]);
138
        $this->assertFalse($testDBO->isLoaded());
139
140
        $this->setupData();
141
        $dbo = $this->getDBOject();
142
        $this->assertFalse($dbo->isLoaded());
143
        $dbo->load(1);
144
        $this->assertTrue($dbo->isLoaded());
145
        $dbo->load(999);
146
        $this->assertFalse($dbo->isLoaded());
147
    }
148
149
    public function testSetLoaded()
150
    {
151
        $testIndex = 'id';
152
153
        $testDBO = new \Suricate\DBObject();
154
        self::mockProperty($testDBO, 'tableIndex', $testIndex);
155
        self::mockProperty($testDBO, 'dbVariables', [
156
            $testIndex,
157
            'name',
158
            'not_loaded_var'
159
        ]);
160
        $this->assertFalse($testDBO->isLoaded());
161
        $testDBO->setLoaded();
162
        $this->assertTrue($testDBO->isLoaded());
163
    }
164
165
    public function testProtected()
166
    {
167
        $testDBO = Category::instanciate([
168
            'id' => 1,
169
            'name' => 'test record'
170
        ]);
171
        $reflector = new ReflectionClass(Category::class);
172
        $property = $reflector->getProperty('protectedValues');
173
        $property->setAccessible(true);
174
        $this->assertSame([], $property->getValue($testDBO));
175
        $this->assertNull($testDBO->unloadable);
0 ignored issues
show
Bug Best Practice introduced by
The property unloadable does not exist on Category. Since you implemented __get, consider adding a @property annotation.
Loading history...
176
177
        $reflector = new ReflectionClass(Category::class);
178
        $property = $reflector->getProperty('protectedValues');
179
        $property->setAccessible(true);
180
        $this->assertSame([], $property->getValue($testDBO));
181
182
        $reflector = new ReflectionClass(Category::class);
183
        $property = $reflector->getProperty('loadedProtectedVariables');
184
        $property->setAccessible(true);
185
        $this->assertSame([], $property->getValue($testDBO));
186
187
        $this->assertSame(42, $testDBO->prot_var);
188
        $property = $reflector->getProperty('protectedValues');
189
        $property->setAccessible(true);
190
        $this->assertSame(['prot_var' => 42], $property->getValue($testDBO));
191
192
        $reflector = new ReflectionClass(Category::class);
193
        $property = $reflector->getProperty('loadedProtectedVariables');
194
        $property->setAccessible(true);
195
        $this->assertSame(['prot_var' => true], $property->getValue($testDBO));
196
    }
197
    public function testInstanciate()
198
    {
199
        $testDBO = Category::instanciate([
200
            'id' => 1,
201
            'name' => 'test record'
202
        ]);
203
204
        $reflector = new ReflectionClass(Category::class);
205
        $property = $reflector->getProperty('dbValues');
206
        $property->setAccessible(true);
207
        $this->assertEquals(
208
            [
209
                'id' => 1,
210
                'name' => 'test record'
211
            ],
212
            $property->getValue($testDBO)
213
        );
214
215
        $this->assertFalse($testDBO->isLoaded());
216
    }
217
218
    public function testHydrate()
219
    {
220
        $testDBO = new \Suricate\DBObject();
221
        $testDBO->realProperty = '';
0 ignored issues
show
Bug Best Practice introduced by
The property realProperty does not exist on Suricate\DBObject. Since you implemented __set, consider adding a @property annotation.
Loading history...
222
223
        self::mockProperty($testDBO, 'dbVariables', ['id', 'name']);
224
        $testDBO->hydrate([
225
            'id' => 1,
226
            'name' => 'test record',
227
            'add_column' => 'test value',
228
            'realProperty' => 'my string'
229
        ]);
230
231
        $this->assertEquals($testDBO->realProperty, 'my string');
0 ignored issues
show
Bug Best Practice introduced by
The property realProperty does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
232
233
        $reflector = new ReflectionClass(get_class($testDBO));
234
        $property = $reflector->getProperty('dbValues');
235
        $property->setAccessible(true);
236
        $this->assertEquals(
237
            [
238
                'id' => 1,
239
                'name' => 'test record'
240
            ],
241
            $property->getValue($testDBO)
242
        );
243
244
        $this->assertFalse($testDBO->isLoaded());
245
    }
246
247
    public function testWakeup()
248
    {
249
        $mock = $this->getMockBuilder(\Suricate\DBObject::class)
250
            ->setMethods(['setRelations'])
251
            ->getMock();
252
253
        $mock->expects($this->once())->method('setRelations');
254
255
        $mock->__wakeup();
0 ignored issues
show
Bug introduced by
The method __wakeup() does not exist on PHPUnit\Framework\MockObject\MockObject. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

255
        $mock->/** @scrutinizer ignore-call */ 
256
               __wakeup();

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
256
    }
257
258
    public function testRelationOneOne()
259
    {
260
        $relations = [
261
            'category' => [
262
                'type' => \Suricate\DBObject::RELATION_ONE_ONE,
263
                'source' => 'category_id',
264
                'target' => 'Category'
265
            ]
266
        ];
267
        // Prepare database
268
        $this->setupData();
269
        $mock = $this->getMockBuilder(\Suricate\DBObject::class)
270
            ->setMethods(['setRelations', 'getRelation'])
271
            ->getMock();
272
273
        // Prepare setup DBObject
274
        $testDBO = $this->getDBOject();
275
        $reflector = new ReflectionClass($mock);
276
        $property = $reflector->getProperty('relations');
277
        $property->setAccessible(true);
278
        $property->setValue($testDBO, $relations);
279
280
        // get relation values
281
        $reflector = new ReflectionClass($testDBO);
282
        $relationValuesRef = $reflector->getProperty('relationValues');
283
        $relationValuesRef->setAccessible(true);
284
285
        $loadedRelationsRef = $reflector->getProperty('loadedRelations');
286
        $loadedRelationsRef->setAccessible(true);
287
288
        // Load
289
        $testDBO->load(1);
290
        $relationsValues = $relationValuesRef->getValue($testDBO);
291
        $loadedRelations = $loadedRelationsRef->getValue($testDBO);
292
293
        // No relation values at first
294
        $this->assertSame([], $relationsValues);
295
        $this->assertSame([], $loadedRelations);
296
        $this->assertEquals('Admin', $testDBO->category->name);
0 ignored issues
show
Bug Best Practice introduced by
The property category does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
297
        $this->assertInstanceOf('\Suricate\DBObject', $testDBO->category);
298
299
        $relationsValues = $relationValuesRef->getValue($testDBO);
300
        $loadedRelations = $loadedRelationsRef->getValue($testDBO);
301
302
        // Check relation cache has been set
303
        $this->assertArrayHasKey('category', $relationsValues);
304
305
        // Check relation loaded flag has been set
306
        $this->assertArrayHasKey('category', $loadedRelations);
307
308
        // Check return type of relation
309
        $this->assertInstanceOf(
310
            '\Suricate\DBObject',
311
            $relationsValues['category']
312
        );
313
314
        // Load new object
315
        $testDBO = $this->getDBOject();
316
        $reflector = new ReflectionClass($mock);
317
        $property = $reflector->getProperty('relations');
318
        $property->setAccessible(true);
319
        $property->setValue($testDBO, $relations);
320
        $testDBO->load(2);
321
        // get relation values
322
        $reflector = new ReflectionClass($testDBO);
323
        $relationValuesRef = $reflector->getProperty('relationValues');
324
        $relationValuesRef->setAccessible(true);
325
326
        $loadedRelationsRef = $reflector->getProperty('loadedRelations');
327
        $loadedRelationsRef->setAccessible(true);
328
329
        $relationsValues = $relationValuesRef->getValue($testDBO);
330
        $loadedRelations = $loadedRelationsRef->getValue($testDBO);
331
332
        // No relation values at first
333
        $this->assertSame([], $relationsValues);
334
        $this->assertSame([], $loadedRelations);
335
336
        // Isset implicit load relation, check that's been loaded
337
        $this->assertTrue(isset($testDBO->category));
338
    }
339
340
    public function testLoad()
341
    {
342
        // Prepare database
343
        $this->setupData();
344
345
        // Inject database handler
346
        $testDBO = $this->getDBOject();
347
348
        $this->assertFalse($testDBO->isLoaded());
349
        $retVal = $testDBO->load(1);
350
        $this->assertTrue($testDBO->isLoaded());
351
        $this->assertEquals(1, $testDBO->id);
0 ignored issues
show
Bug Best Practice introduced by
The property id does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
352
353
        $this->assertEquals('John', $testDBO->name);
0 ignored issues
show
Bug Best Practice introduced by
The property name does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
354
355
        $this->assertInstanceOf('\Suricate\DBObject', $retVal);
356
    }
357
358
    public function testSetInsertIgnore()
359
    {
360
        $testDBO = $this->getDBOject();
361
        $reflectionClass = new \ReflectionClass($testDBO);
362
363
        $property = $reflectionClass->getProperty('insertIgnore');
364
        $property->setAccessible(true);
365
366
        $this->assertFalse($property->getValue($testDBO));
367
        $retVal = $testDBO->setInsertIgnore(true);
368
        $this->assertInstanceOf('\Suricate\DBObject', $retVal);
369
370
        $this->assertTrue($property->getValue($testDBO));
371
    }
372
373
    public function testSaveUpdate()
374
    {
375
        // Prepare database
376
        $this->setupData();
377
378
        // Simple save
379
        $testDBO = $this->getDBOject();
380
        $testDBO->id = 55;
0 ignored issues
show
Bug Best Practice introduced by
The property id does not exist on Suricate\DBObject. Since you implemented __set, consider adding a @property annotation.
Loading history...
381
        $testDBO->name = 'Steve';
0 ignored issues
show
Bug Best Practice introduced by
The property name does not exist on Suricate\DBObject. Since you implemented __set, consider adding a @property annotation.
Loading history...
382
        $testDBO->date_added = '2019-01-27';
0 ignored issues
show
Bug Best Practice introduced by
The property date_added does not exist on Suricate\DBObject. Since you implemented __set, consider adding a @property annotation.
Loading history...
383
        $testDBO->save();
384
385
        $loaded = $this->getDBOject();
386
        $retVal = $loaded->load(55);
387
        $this->assertTrue($testDBO->isLoaded());
388
        $this->assertEquals(55, $loaded->id);
0 ignored issues
show
Bug Best Practice introduced by
The property id does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
389
        $this->assertEquals('Steve', $loaded->name);
0 ignored issues
show
Bug Best Practice introduced by
The property name does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
390
        $this->assertInstanceOf('\Suricate\DBObject', $retVal);
391
392
        // Update
393
        $loaded->name = 'Tim';
394
        $loaded->save();
395
        $loaded = $this->getDBOject();
396
        $retVal = $loaded->load(55);
397
        $this->assertTrue($testDBO->isLoaded());
398
        $this->assertEquals(55, $loaded->id);
399
        $this->assertEquals('Tim', $loaded->name);
400
        $this->assertInstanceOf('\Suricate\DBObject', $retVal);
401
    }
402
403
    public function testForceInsert()
404
    {
405
        // Prepare database
406
        $this->setupData();
407
408
        // Force insert
409
        $loadedForce = $this->getDBOject();
410
        $retVal = $loadedForce->load(1);
0 ignored issues
show
Unused Code introduced by
The assignment to $retVal is dead and can be removed.
Loading history...
411
        $loadedForce->id = 56;
0 ignored issues
show
Bug Best Practice introduced by
The property id does not exist on Suricate\DBObject. Since you implemented __set, consider adding a @property annotation.
Loading history...
412
        $loadedForce->save(true);
413
414
        $loaded = $this->getDBOject();
415
        $retVal = $loaded->load(56);
416
417
        $this->assertEquals(56, $loaded->id);
0 ignored issues
show
Bug Best Practice introduced by
The property id does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
418
        $this->assertEquals('John', $loaded->name);
0 ignored issues
show
Bug Best Practice introduced by
The property name does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
419
        $this->assertInstanceOf('\Suricate\DBObject', $retVal);
420
    }
421
422
    public function testDelete()
423
    {
424
        // Prepare database
425
        $this->setupData();
426
427
        // Simple save
428
        $testDBO = $this->getDBOject();
429
        $testDBO->id = 55;
0 ignored issues
show
Bug Best Practice introduced by
The property id does not exist on Suricate\DBObject. Since you implemented __set, consider adding a @property annotation.
Loading history...
430
        $testDBO->name = 'Steve';
0 ignored issues
show
Bug Best Practice introduced by
The property name does not exist on Suricate\DBObject. Since you implemented __set, consider adding a @property annotation.
Loading history...
431
        $testDBO->date_added = '2019-01-27';
0 ignored issues
show
Bug Best Practice introduced by
The property date_added does not exist on Suricate\DBObject. Since you implemented __set, consider adding a @property annotation.
Loading history...
432
        $testDBO->save();
433
434
        $testDBO = $this->getDBOject();
435
        $retVal = $testDBO->loadOrFail(55);
436
        $this->assertInstanceOf('\Suricate\DBObject', $retVal);
437
438
        $testDBO->delete();
439
440
        $testDBO = $this->getDBOject();
441
        $this->expectException(
442
            \Suricate\Exception\ModelNotFoundException::class
443
        );
444
        $testDBO->loadOrFail(55);
445
    }
446
447
    public function testLoadFromSQL()
448
    {
449
        // Prepare database
450
        $this->setupData();
451
452
        // Inject database handler
453
        $testDBO = $this->getDBOject();
454
455
        $sql = "SELECT * FROM `users` WHERE id=:id";
456
        $params = ['id' => 1];
457
458
        $retVal = $testDBO->loadFromSql($sql, $params);
459
        $this->assertInstanceOf('\Suricate\DBObject', $retVal);
460
        $this->assertTrue($testDBO->isLoaded());
461
462
        $params = ['id' => 100];
463
        $retVal = $testDBO->loadFromSql($sql, $params);
464
        $this->assertFalse($retVal);
465
        $this->assertFalse($testDBO->isLoaded());
466
    }
467
468
    public function testLoadOrFail()
469
    {
470
        // Prepare database
471
        $this->setupData();
472
473
        // Inject database handler
474
        $testDBO = $this->getDBOject();
475
476
        $retVal = $testDBO->loadOrFail(1);
477
        $this->assertInstanceOf('\Suricate\DBObject', $retVal);
478
479
        $this->expectException(
480
            \Suricate\Exception\ModelNotFoundException::class
481
        );
482
        $testDBO->loadOrFail(100);
483
    }
484
485
    public function testLoadOrInstanciate()
486
    {
487
        // Prepare database
488
        $this->setupData();
489
490
        $testDBO = Category::loadOrInstanciate(100);
491
492
        $comparison = $this->getCategoryDBOject();
493
        $comparison->load(100);
494
495
        $this->assertInstanceOf('\Suricate\DBObject', $testDBO);
496
        $this->assertInstanceOf('Category', $testDBO);
497
498
        $this->assertSame($comparison->id, $testDBO->id);
0 ignored issues
show
Bug Best Practice introduced by
The property id does not exist on Category. Since you implemented __get, consider adding a @property annotation.
Loading history...
Bug Best Practice introduced by
The property id does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
499
        $this->assertSame($comparison->name, $testDBO->name);
0 ignored issues
show
Bug Best Practice introduced by
The property name does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
Bug Best Practice introduced by
The property name does not exist on Category. Since you implemented __get, consider adding a @property annotation.
Loading history...
500
        $this->assertTrue($testDBO->isLoaded());
501
502
        // non existing
503
        $testDBO = Category::loadOrInstanciate(102);
504
        $this->assertFalse($testDBO->isLoaded()); // has been instanciated, not loaded
505
        $this->assertSame($testDBO->id, "102");
506
        $this->assertSame($testDBO->name, null);
507
508
        $testDBO = Category::loadOrInstanciate([
509
            'id' => 102,
510
            'name' => 'test name'
511
        ]);
512
        $this->assertFalse($testDBO->isLoaded());
513
        $this->assertSame($testDBO->id, "102");
514
        $this->assertSame($testDBO->name, 'test name');
515
516
        $testDBO = Category::loadOrInstanciate([
517
            'id' => 101,
518
            'name' => 'test name'
519
        ]);
520
        $this->assertFalse($testDBO->isLoaded());
521
        $this->assertSame($testDBO->id, "101");
522
        $this->assertSame($testDBO->name, 'test name');
523
524
        $testDBO = Category::loadOrInstanciate([
525
            'id' => 101,
526
            'name' => 'Employee'
527
        ]);
528
        $this->assertTrue($testDBO->isLoaded());
529
        $this->assertSame($testDBO->id, "101");
530
        $this->assertSame($testDBO->name, 'Employee');
531
    }
532
533
    public function testCreate()
534
    {
535
        // Prepare database
536
        $this->setupData();
537
        $comparison = $this->getCategoryDBOject();
538
539
        $testDBO = Category::create(['id' => 1020]);
540
541
        $this->assertInstanceOf('\Suricate\DBObject', $testDBO);
542
        $this->assertTrue($testDBO->isLoaded());
543
544
        $comparison->load(1020);
545
546
        $this->assertSame($comparison->id, $testDBO->id);
0 ignored issues
show
Bug Best Practice introduced by
The property id does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
Bug Best Practice introduced by
The property id does not exist on Category. Since you implemented __get, consider adding a @property annotation.
Loading history...
547
        $this->assertSame($comparison->name, null);
0 ignored issues
show
Bug Best Practice introduced by
The property name does not exist on Suricate\DBObject. Since you implemented __get, consider adding a @property annotation.
Loading history...
548
    }
549
550
    public function testToArray()
551
    {
552
        // Prepare database
553
        $this->setupData();
554
555
        // Inject database handler
556
        $testDBO = $this->getDBOject();
557
        $testDBO->load(2);
558
559
        $this->assertSame(
560
            [
561
                'id' => '2',
562
                'category_id' => '100',
563
                'name' => 'Paul',
564
                'date_added' => '2019-01-11 00:00:00'
565
            ],
566
            $testDBO->toArray()
567
        );
568
569
        $testDBO = $this->getDBOject();
570
        $testDBO->load(2);
571
        self::mockProperty($testDBO, 'exportedVariables', [
572
            'id' => 'id',
573
            'category_id' => 'category_id,type:integer',
574
            'name' => ',omitempty',
575
            'date_added' => '-'
576
        ]);
577
        $testDBO->name = '';
0 ignored issues
show
Bug Best Practice introduced by
The property name does not exist on Suricate\DBObject. Since you implemented __set, consider adding a @property annotation.
Loading history...
578
579
        $this->assertSame(
580
            [
581
                'id' => '2',
582
                'category_id' => 100
583
            ],
584
            $testDBO->toArray()
585
        );
586
    }
587
588
    public function testToJson()
589
    {
590
        // Prepare database
591
        $this->setupData();
592
593
        // Inject database handler
594
        $testDBO = $this->getDBOject();
595
        $testDBO->load(2);
596
597
        $this->assertSame(
598
            '{"id":"2","category_id":"100","name":"Paul","date_added":"2019-01-11 00:00:00"}',
599
            $testDBO->toJson()
600
        );
601
    }
602
603
    public function testValidate()
604
    {
605
        $testDBO = $this->getDBOject();
606
        $this->assertTrue($testDBO->validate());
607
    }
608
609
    public static function mockProperty($object, string $propertyName, $value)
610
    {
611
        $reflectionClass = new \ReflectionClass($object);
612
613
        $property = $reflectionClass->getProperty($propertyName);
614
        $property->setAccessible(true);
615
        $property->setValue($object, $value);
616
        $property->setAccessible(false);
617
    }
618
619
    protected function setupData()
620
    {
621
        $pdo = new PDO('sqlite:/tmp/test.db');
622
        $pdo->exec("DROP TABLE IF EXISTS `users`");
623
        $pdo->exec("DROP TABLE IF EXISTS `categories`");
624
        $pdo->exec(
625
            "CREATE TABLE `users` (`id` INTEGER PRIMARY KEY,`category_id` INTEGER, `name` varchar(50) DEFAULT NULL,`date_added` datetime NOT NULL)"
626
        );
627
        $pdo->exec(
628
            "CREATE TABLE `categories` (`id` INTEGER PRIMARY KEY, `name` varchar(50) DEFAULT NULL, `parent_id` INTEGER DEFAULT NULL)"
629
        );
630
631
        $stmt = $pdo->prepare(
632
            "INSERT INTO `users` (name, category_id, date_added) VALUES (:name, :categoryid, :date)"
633
        );
634
        $values = [
635
            ['John', 100, '2019-01-10 00:00:00'],
636
            ['Paul', 100, '2019-01-11 00:00:00'],
637
            ['Robert', 101, '2019-01-12 00:00:00']
638
        ];
639
        foreach ($values as $value) {
640
            $stmt->execute([
641
                'name' => $value[0],
642
                'categoryid' => $value[1],
643
                'date' => $value[2]
644
            ]);
645
        }
646
647
        $stmt = $pdo->prepare(
648
            "INSERT INTO `categories` (id, name) VALUES (:id, :name)"
649
        );
650
        $values = [[100, 'Admin'], [101, 'Employee']];
651
        foreach ($values as $value) {
652
            $stmt->execute(['id' => $value[0], 'name' => $value[1]]);
653
        }
654
    }
655
656
    protected function getDatabase()
657
    {
658
        $database = new \Suricate\Database();
659
        $database->configure([
660
            'type' => 'sqlite',
661
            'file' => '/tmp/test.db'
662
        ]);
663
664
        return $database;
665
    }
666
667
    protected function getDBOject()
668
    {
669
        $dbLink = $this->getDatabase();
670
        // Inject database handler
671
        $testDBO = new \Suricate\DBObject();
672
673
        $reflector = new ReflectionClass(get_class($testDBO));
674
        $property = $reflector->getProperty('dbLink');
675
        $property->setAccessible(true);
676
        $property->setValue($testDBO, $dbLink);
677
678
        self::mockProperty($testDBO, 'tableName', $this->tableName);
679
        self::mockProperty($testDBO, 'tableIndex', 'id');
680
        self::mockProperty($testDBO, 'dbVariables', [
681
            'id',
682
            'category_id',
683
            'name',
684
            'date_added'
685
        ]);
686
687
        return $testDBO;
688
    }
689
690
    protected function getCategoryDBOject()
691
    {
692
        $dbLink = $this->getDatabase();
693
        // Inject database handler
694
        $testDBO = new \Suricate\DBObject();
695
696
        $reflector = new ReflectionClass(get_class($testDBO));
697
        $property = $reflector->getProperty('dbLink');
698
        $property->setAccessible(true);
699
        $property->setValue($testDBO, $dbLink);
700
701
        self::mockProperty($testDBO, 'tableName', 'categories');
702
        self::mockProperty($testDBO, 'tableIndex', 'id');
703
        self::mockProperty($testDBO, 'dbVariables', ['id', 'name']);
704
705
        return $testDBO;
706
    }
707
}
708