Completed
Push — master ( 85c97a...a6409c )
by Matteo
16:08 queued 07:17
created

tests/GitElephant/RepositoryTest.php (3 issues)

Labels
Severity

Upgrade to new PHP Analysis Engine

These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more

1
<?php
2
3
/**
4
 * This file is part of the GitElephant package.
5
 *
6
 * (c) Matteo Giachino <[email protected]>
7
 *
8
 * For the full copyright and license information, please view the LICENSE
9
 * file that was distributed with this source code.
10
 *
11
 * Just for fun...
12
 */
13
14
namespace GitElephant;
15
16
use \GitElephant\Objects\Branch;
17
use \GitElephant\Objects\Object;
18
use \GitElephant\Objects\Tag;
19
20
/**
21
 * RepositoryTest
22
 *
23
 * Repository Test Class
24
 *
25
 * @author Matteo Giachino <[email protected]>
26
 */
27
28
class RepositoryTest extends TestCase
29
{
30
    /**
31
     * setUp
32
     */
33
    public function setUp()
34
    {
35
        $this->initRepository();
36
    }
37
38
    /**
39
     * @covers GitElephant\Repository::__construct
40
     * @covers GitElephant\Repository::getPath
41
     */
42
    public function testConstruct()
43
    {
44
        $this->assertEquals($this->getRepository()->getPath(), $this->path);
45
46
        $this->setExpectedException('GitElephant\Exception\InvalidRepositoryPathException');
47
        $repo = new Repository('non-existent-path');
48
49
        $repo = Repository::open($this->path);
50
        $this->assertInstanceOf('GitElephant\Repository', $repo);
51
    }
52
53
    /**
54
     * @covers GitElephant\Repository::init
55
     */
56
    public function testInit()
57
    {
58
        $this->getRepository()->init();
59
        $match = false;
60
61
        // Force US/EN locale
62
        putenv('LANG=en_US.UTF-8');
63
64
        foreach ($this->getRepository()->getStatusOutput() as $line) {
65
            if (preg_match('/nothing to commit?(.*)/', $line)) {
66
                $match = true;
67
            }
68
        }
69
        $this->assertTrue($match, 'init problem, git status on an empty repo should give nothing to commit');
70
    }
71
72
    /**
73
     * testName
74
     */
75
    public function testName()
76
    {
77
        $this->getRepository()->setName('test-repo');
78
        $this->assertEquals('test-repo', $this->getRepository()->getName());
79
    }
80
81
    /**
82
     * @covers GitElephant\Repository::stage
83
     */
84
    public function testStage()
85
    {
86
        $this->getRepository()->init();
87
        $this->addFile('test');
88
        $this->getRepository()->stage();
89
        $match = false;
90
        foreach ($this->getRepository()->getStatusOutput() as $line) {
91
            if (preg_match('/(.*)Changes to be committed(.*)/', $line)) {
92
                $match = true;
93
            }
94
        }
95
        $this->assertTrue($match, 'stageAll error, git status should give Changes to be committed');
96
    }
97
98
    /**
99
     * @covers GitElephant\Repository::unstage
100
     */
101
    public function testUnstage()
102
    {
103
        $this->getRepository()->init();
104
        $this->addFile('test');
105
        $this->getRepository()->commit('first commit', true);
106
        $this->addFile('test2');
107
        $this->assertCount(1, $this->getRepository()->getStatus()->untracked());
108
        $this->assertCount(0, $this->getRepository()->getStatus()->added());
109
        $this->getRepository()->stage('test2');
110
        $this->assertCount(0, $this->getRepository()->getStatus()->untracked());
111
        $this->assertCount(1, $this->getRepository()->getStatus()->added());
112
        $this->getRepository()->unstage('test2');
113
        $this->assertCount(1, $this->getRepository()->getStatus()->untracked());
114
        $this->assertCount(0, $this->getRepository()->getStatus()->added());
115
    }
116
117
    /**
118
     * @covers GitElephant\Repository::commit
119
     * @covers GitElephant\Repository::getStatusOutput
120
     */
121
    public function testCommit()
122
    {
123
        $this->getRepository()->init();
124
        $this->addFile('test');
125
        $this->getRepository()->stage();
126
        $this->getRepository()->commit('initial import');
127
        $match = false;
128
        foreach ($this->getRepository()->getStatusOutput() as $line) {
129
            if (preg_match('/nothing to commit?(.*)/', $line)) {
130
                $match = true;
131
            }
132
        }
133
        $this->assertTrue($match, 'commit error, git status should give nothing to commit');
134
135
        $this->getRepository()->createBranch('develop', $this->getRepository()->getCommit());
136
        $this->addFile('test2');
137
        $this->getRepository()->commit('commit 2', true, 'develop');
138
        $match = false;
139
        foreach ($this->getRepository()->getStatusOutput() as $line) {
140
            if (preg_match('/nothing to commit?(.*)/', $line)) {
141
                $match = true;
142
            }
143
        }
144
        $this->assertTrue($match, 'commit error, git status should give nothing to commit');
145
    }
146
147
    /**
148
     * @covers GitElephant\Repository::getStatusOutput
149
     */
150
    public function testGetStatus()
151
    {
152
        $this->getRepository()->init();
153
        $this->addFile('test');
154
        $this->getRepository()->commit('test commit', true);
155
        $output = $this->getRepository()->getStatusOutput();
156
        $this->assertStringEndsWith('master', $output[0]);
157
        $this->addFile('file2');
158
        $output = $this->getRepository()->getStatusOutput();
159
        $this->assertStringEndsWith('file2', $output[4]);
160
    }
161
162
    /**
163
     * @covers GitElephant\Repository::createBranch
164
     */
165
    public function testCreateBranch()
166
    {
167
        $this->getRepository()->init();
168
        $this->addFile('test');
169
        $this->getRepository()->commit('foo', true);
170
        $this->getRepository()->createBranch('test-branch');
171
        $this->assertEquals(2, count($this->getRepository()->getBranches()));
172
    }
173
174
    /**
175
     * @covers GitElephant\Repository::deleteBranch
176
     */
177
    public function testDeleteBranch()
178
    {
179
        $this->getRepository()->init();
180
        $this->addFile('test-file');
181
        $this->getRepository()->commit('test', true);
182
        $this->getRepository()->createBranch('branch2');
183
        $this->assertEquals(2, count($this->getRepository()->getBranches(true)));
184
        $this->getRepository()->deleteBranch('branch2');
185
        $this->assertEquals(1, count($this->getRepository()->getBranches(true)));
186
        $this->addFile('test-file2');
187
        $this->getRepository()->commit('test2', true);
188
        $this->getRepository()->createBranch('branch3');
189
        $this->assertEquals(2, count($this->getRepository()->getBranches(true)));
190
        $this->getRepository()->deleteBranch('branch3', true);
191
        $this->assertEquals(1, count($this->getRepository()->getBranches(true)));
192
    }
193
194
    /**
195
     * @covers GitElephant\Repository::getBranches
196
     */
197
    public function testGetBranches()
198
    {
199
        $this->getRepository()->init();
200
        $this->addFile('test');
201
        $this->getRepository()->stage();
202
        $this->getRepository()->commit('initial import', true);
203
        $this->assertCount(
204
            1,
205
            $this->getRepository()->getBranches(),
206
            'an initialized repository should have only one branch'
207
        );
208
        $this->getRepository()->createBranch('test-branch');
209
        $this->assertCount(2, $this->getRepository()->getBranches(), 'two branches expected');
210
        $branches = $this->getRepository()->getBranches();
211
        $this->assertEquals('master', $branches[0]->getName());
212
        $this->getRepository()->deleteBranch('test-branch');
213
        $this->assertCount(1, $this->getRepository()->getBranches(), 'one branch expected');
214
        $mainBranch = $this->getRepository()->getMainBranch();
215
        $this->assertInstanceOf(
216
            'GitElephant\Objects\Branch',
217
            $this->getRepository()->getMainBranch(),
218
            'main branch should be an instance of Branch'
219
        );
220
        $this->assertTrue(
221
            $this->getRepository()->getMainBranch()->getCurrent(),
222
            'getCurrent on main branch should be true'
223
        );
224
        $this->assertEquals(
225
            'master',
226
            $this->getRepository()->getMainBranch()->getName(),
227
            'main branch should be named "master"'
228
        );
229
        $this->assertEquals(array('master'), $this->getRepository()->getBranches(true));
230
        $this->getRepository()->createBranch('develop');
231
        $this->assertContains('master', $this->getRepository()->getBranches(true));
232
        $this->assertContains('develop', $this->getRepository()->getBranches(true));
233
    }
234
235
    /**
236
     * @covers GitElephant\Repository::getMainBranch
237
     */
238
    public function testGetMainBranch()
239
    {
240
        $this->getRepository()->init();
241
        $this->addFile('test-file');
242
        $this->getRepository()->commit('test', true);
243
        $this->assertEquals('master', $this->getRepository()->getMainBranch()->getName());
244
    }
245
246
    /**
247
     * @covers GitElephant\Repository::getBranch
248
     */
249
    public function testGetBranch()
250
    {
251
        $this->getRepository()->init();
252
        $this->addFile('test-file');
253
        $this->getRepository()->commit('test', true);
254
        $this->assertInstanceOf('GitElephant\Objects\Branch', $this->getRepository()->getBranch('master'));
255
        $this->assertNull($this->getRepository()->getBranch('a-branch-that-do-not-exists'));
256
    }
257
258
    /**
259
     * @covers GitElephant\Repository::merge
260
     */
261
    public function testMerge()
262
    {
263
        $this->getRepository()->init();
264
        $this->addFile('test-file');
265
        $this->getRepository()->commit('test', true);
266
        $this->assertEquals(1, count($this->getRepository()->getTree()));
267
        $this->getRepository()->createBranch('branch2');
268
        $this->getRepository()->checkout('branch2');
269
        $this->addFile('file2');
270
        $this->getRepository()->commit('test2', true);
271
        $this->assertEquals(2, count($this->getRepository()->getTree()));
272
        $this->getRepository()->checkout('master');
273
        $this->assertEquals(1, count($this->getRepository()->getTree()));
274
        $this->getRepository()->merge($this->getRepository()->getBranch('branch2'));
275
        $this->assertEquals(2, count($this->getRepository()->getTree()));
276
277
        // attempt to merge a different branch by forcing a 3-way merge and verify the merge commit message
278
        $this->getRepository()->createBranch('branch3');
279
        $this->getRepository()->checkout('branch3');
280
        $this->addFile('file3');
281
        $this->getRepository()->commit('test3', true);
282
        $this->assertEquals(3, count($this->getRepository()->getTree()));
283
        $this->getRepository()->checkout('master');
284
        $this->assertEquals(2, count($this->getRepository()->getTree()));
285
        $this->getRepository()->merge($this->getRepository()->getBranch('branch3'), 'test msg', 'no-ff');
286
        $this->assertEquals(3, count($this->getRepository()->getTree()));
287
        $this->assertEquals('test msg', $this->getRepository()->getCommit()->getMessage()->getFullMessage());
288
289
        // attempt a fast forward merge where a 3-way is necessary and trap the resulting exception
290
        $this->getRepository()->checkout('branch2');
291
        $this->addFile('file4');
292
        $this->getRepository()->commit('test4', true);
293
        $this->assertEquals(3, count($this->getRepository()->getTree()));
294
        $this->getRepository()->checkout('master');
295
        $this->assertEquals(3, count($this->getRepository()->getTree()));
296
        try {
297
            $this->getRepository()->merge($this->getRepository()->getBranch('branch2'), '', 'ff-only');
298
        } catch (\RuntimeException $e) {
299
            return;
300
        }
301
        $this->fail("Merge should have produced a runtime exception.");
302
    }
303
304
    /**
305
     * @covers GitElephant\Repository::getTags
306
     * @covers GitElephant\Repository::getTag
307
     * @covers GitElephant\Repository::createTag
308
     * @covers GitElephant\Repository::deleteTag
309
     */
310
    public function testTags()
311
    {
312
        $this->getRepository()->init();
313
        $this->addFile('test-file');
314
        $this->getRepository()->commit('test', true);
315
        $this->assertEquals(0, count($this->getRepository()->getTags()));
316
        $this->getRepository()->createTag('test-tag');
317
        $this->assertEquals(1, count($this->getRepository()->getTags()));
318
        $this->assertInstanceOf('GitElephant\Objects\Tag', $this->getRepository()->getTag('test-tag'));
319
        $this->getRepository()->deleteTag('test-tag');
320
        $this->assertEquals(0, count($this->getRepository()->getTags()));
321
        $this->assertNull($this->getRepository()->getTag('a-tag-that-do-not-exists'));
322
    }
323
324
    /**
325
     * test getLastTag
326
     */
327
    public function testGetLastTag()
328
    {
329
        $this->getRepository()->init();
330
        $this->addFile('test-file');
331
        $this->getRepository()->commit('test', true);
332
        $this->getRepository()->createTag('0.0.2');
333
        sleep(1);
334
        $this->getRepository()->createTag('0.0.4');
335
        sleep(1);
336
        $this->getRepository()->createTag('0.0.3');
337
        sleep(1);
338
        $this->getRepository()->createTag('0.0.1');
339
        sleep(1);
340
        $this->assertEquals(Tag::pick($this->getRepository(), '0.0.1'), $this->getRepository()->getLastTag());
341
        $this->getRepository()->createTag('0.0.05');
342
        $this->assertEquals(Tag::pick($this->getRepository(), '0.0.05'), $this->getRepository()->getLastTag());
343
        $this->getRepository()->deleteTag(Tag::pick($this->getRepository(), '0.0.05'));
344
        $this->assertEquals(Tag::pick($this->getRepository(), '0.0.1'), $this->getRepository()->getLastTag());
345
    }
346
347
    /**
348
     * @covers GitElephant\Repository::getCommit
349
     */
350
    public function testGetCommit()
351
    {
352
        $this->getRepository()->init();
353
        $this->addFile('test-file');
354
        $this->getRepository()->commit('test', true);
355
        $this->assertInstanceOf('GitElephant\Objects\Commit', $this->getRepository()->getCommit());
356
    }
357
358
    public function testGetBranchOrTag()
359
    {
360
        $this->getRepository()->init();
361
        $this->addFile('test-file');
362
        $this->getRepository()->commit('test', true);
363
        $this->getRepository()->createBranch('branch2');
364
        $this->getRepository()->createTag('tag1');
365
        $this->assertInstanceOf('\GitElephant\Objects\Branch', $this->getRepository()->getBranchOrTag('branch2'));
366
        $this->assertInstanceOf('\GitElephant\Objects\Tag', $this->getRepository()->getBranchOrTag('tag1'));
367
        $this->assertNull($this->getRepository()->getBranchOrTag('not-exists'));
368
    }
369
370
    /**
371
     * @covers GitElephant\Repository::getObjectLog
372
     */
373
    public function testGetObjectLog()
374
    {
375
        $repo = $this->getRepository();
376
        $repo->init();
377
378
        $this->addFolder('test');
379
380
        $this->addFile('A.txt', 'test');
381
        $repo->commit('added A.txt', true);
382
383
        $this->addFile('B.txt', 'test');
384
        $repo->commit('added B.txt', true);
385
386
        $this->addFile('C.txt', 'test');
387
        $repo->commit('added C.txt', true);
388
389
        $this->addFile('D.txt', 'test');
390
        $repo->commit('added D.txt', true);
391
392
        $this->addFile('E.txt', 'test');
393
        $repo->commit('added E.txt', true);
394
395
        $tree = $repo->getTree();
396
        $obj = $tree[0];
397
398
        $log = $this->getRepository()->getObjectLog($obj);
399
        $this->assertInstanceOf('GitElephant\Objects\Log', $log);
400
        $this->assertEquals(1, $log->count());
401
402
        $log = $this->getRepository()->getObjectLog($obj, null, null, null);
403
        $this->assertEquals(5, $log->count());
404
405
        $this->assertEquals('added E.txt', $log->first()->getMessage()->toString());
406
        $this->assertEquals('added A.txt', $log->last()->getMessage()->toString());
407
    }
408
409
    /**
410
     * Test logs on different tree objects
411
     *
412
     * @covers GitElephant\Repository::getObjectLog
413
     */
414
    public function testGetObjectLogFolders()
415
    {
416
        $repo = $this->getRepository();
417
        $repo->init();
418
419
        $this->addFolder('A');
420
        $this->addFile('A1.txt', 'A');
421
        $repo->commit('A/A1', true);
422
423
        $this->addFile('A2.txt', 'A');
424
        $repo->commit('A/A2', true);
425
426
        $this->addFolder('B');
427
        $this->addFile('B1.txt', 'B');
428
        $repo->commit('B/B1', true);
429
430
        $this->addFile('B2.txt', 'B');
431
        $repo->commit('B/B2', true);
432
433
        $tree = $repo->getTree();
434
435
        /* @var $treeObj Object */
436
        foreach ($tree as $treeObj) {
437
            $name = $treeObj->getName();
438
            $log = $repo->getObjectLog($treeObj, null, null, null);
439
440
            $this->assertEquals(2, $log->count());
441
442
            $i = 2;
443
            foreach ($log as $commit) {
444
                $this->assertEquals($name . '/' . $name . $i, $commit->getMessage()->toString());
445
                --$i;
446
            }
447
        }
448
    }
449
450
    /**
451
     * Test logs on different branches
452
     *
453
     * @covers GitElephant\Repository::getObjectLog
454
     */
455
    public function testGetObjectLogBranches()
456
    {
457
        $repo = $this->getRepository();
458
        $repo->init();
459
460
        $this->addFolder('A');
461
        $this->addFile('A1.txt', 'A');
462
        $repo->commit('A/A1', true);
463
464
        $this->addFile('A2.txt', 'A');
465
        $repo->commit('A/A2', true);
466
467
        $repo->createBranch('test-branch');
468
        $repo->checkout('test-branch');
469
470
        $this->addFile('A3.txt', 'A');
471
        $repo->commit('A/A3', true);
472
473
        // master branch
474
        $repo->checkout('master');
475
        $tree = $repo->getTree();
476
        $dir = $tree[0];
477
        $log = $repo->getObjectLog($dir, null, null, null);
478
479
        $this->assertEquals(2, $log->count());
480
        $this->assertEquals('A/A2', $log->first()->getMessage()->toString());
481
482
        // test branch
483
        $repo->checkout('test-branch');
484
        $tree = $repo->getTree();
485
        $dir = $tree[0];
486
        $log = $repo->getObjectLog($dir, null, null, null);
487
488
        $this->assertEquals(3, $log->count());
489
        $this->assertEquals('A/A3', $log->first()->getMessage()->toString());
490
    }
491
492
    /**
493
     * @covers GitElephant\Repository::getLog
494
     */
495
    public function testGetLog()
496
    {
497
        $this->getRepository()->init();
498
499
        for ($i = 0; $i < 50; $i++) {
500
            $this->addFile('test file ' . $i);
501
            $this->getRepository()->commit('test commit ' . $i, true);
502
        }
503
504
        $log = $this->getRepository()->getLog();
505
        $this->assertInstanceOf('GitElephant\Objects\Log', $this->getRepository()->getLog());
506
        $this->assertGreaterThan(0, $log->count());
507
    }
508
509
    /**
510
     * @covers GitElephant\Repository::getLog
511
     */
512
    public function testGetLog_for_a_branch()
513
    {
514
        $this->getRepository()->init();
515
        $this->addFile('test file 0');
516
        $this->getRepository()->commit('first commit', true);
517
        $this->getRepository()->checkout('test-branch', true);
518
519
        for ($i = 1; $i <= 2; $i++) {
520
            $this->addFile('test file ' . $i);
521
            $this->getRepository()->commit('test commit ' . $i, true);
522
        }
523
524
        $log = $this->getRepository()->getLog(array('test-branch', '^master'));
525
        $this->assertInstanceOf('GitElephant\Objects\Log', $this->getRepository()->getLog());
526
        $this->assertEquals(2, $log->count());
527
    }
528
529
    /**
530
     * @covers GitElephant\Repository::checkout
531
     */
532
    public function testCheckout()
533
    {
534
        $this->getRepository()->init();
535
        $this->addFile('test-file');
536
        $this->getRepository()->commit('test', true);
537
        $this->assertEquals('master', $this->getRepository()->getMainBranch()->getName());
538
        $this->getRepository()->createBranch('branch2');
539
        $this->getRepository()->checkout('branch2');
540
        $this->assertEquals('branch2', $this->getRepository()->getMainBranch()->getName());
541
    }
542
543
    /**
544
     * @covers GitElephant\Repository::checkout
545
     */
546
    public function testCheckoutTag()
547
    {
548
        $this->getRepository()->init();
549
        $this->addFile('test-file');
550
        $this->getRepository()->commit('test', true);
551
        $this->getRepository()->createTag('v0.0.1');
552
        $this->addFile('test-file2');
553
        $this->getRepository()->commit('test2', true);
554
        $tag = $this->getRepository()->getTag('v0.0.1');
555
        $this->assertInstanceOf('GitElephant\Objects\Tag', $tag);
556
        $lastCommit = $this->getRepository()->getCommit();
557
        $this->assertNotContains('detached', implode(' ', $this->getRepository()->getStatusOutput()));
558
        $this->getRepository()->checkout($tag);
0 ignored issues
show
It seems like $tag defined by $this->getRepository()->getTag('v0.0.1') on line 554 can be null; however, GitElephant\Repository::checkout() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
559
        $newCommit = $this->getRepository()->getCommit();
560
        $this->assertNotEquals($newCommit->getSha(), $lastCommit->getSha());
561
        $this->assertContains('detached', implode(' ', $this->getRepository()->getStatusOutput()));
562
    }
563
564
    /**
565
     * @covers GitElephant\Repository::getTree
566
     * @covers GitElephant\Objects\Tree
567
     */
568
    public function testGetTree()
569
    {
570
        $this->getRepository()->init();
571
        $this->addFile('test');
572
        $this->addFolder('test-folder');
573
        $this->addFile('test2', 'test-folder');
574
575
        $this->getRepository()->stage();
576
        $this->getRepository()->commit('initial import');
577
578
        $tree = $this->getRepository()->getTree();
579
        $this->assertFalse($tree->isBlob());
580
        $this->assertTrue($this->getRepository()->getTree($this->getRepository()->getCommit(), 'test')->isBlob());
581
        $this->assertCount(2, $tree, 'One file in the repository');
582
        $firstNode = $tree[0];
583
        $this->assertInstanceOf(
584
            'GitElephant\Objects\Object',
585
            $firstNode,
586
            'array access on tree should give always a node type'
587
        );
588
        $this->assertEquals(
589
            'test-folder',
590
            $firstNode->getName(),
591
            'First repository file should be named "test"'
592
        );
593
        $secondNode = $tree[1];
594
        $this->assertInstanceOf(
595
            'GitElephant\Objects\Object',
596
            $secondNode,
597
            'array access on tree should give always a node type'
598
        );
599
        $this->assertEquals(
600
            Object::TYPE_BLOB,
601
            $secondNode->getType(),
602
            'second node should be of type tree'
603
        );
604
        $subtree = $this->getRepository()->getTree('master', 'test-folder');
605
        $subnode = $subtree[0];
606
        $this->assertInstanceOf(
607
            'GitElephant\Objects\Object',
608
            $subnode,
609
            'array access on tree should give always a node type'
610
        );
611
        $this->assertEquals(
612
            Object::TYPE_BLOB,
613
            $subnode->getType(),
614
            'subnode should be of type blob'
615
        );
616
        $this->assertEquals(
617
            'test2',
618
            $subnode->getName(),
619
            'subnode should be named "test2"'
620
        );
621
    }
622
623
    /**
624
     * @covers GitElephant\Repository::getDiff
625
     */
626
    public function testGetDiff()
627
    {
628
        $this->getRepository()->init();
629
        $this->addFile('test-file');
630
        $this->getRepository()->commit('commit 1', true);
631
        $commit1 = $this->getRepository()->getCommit();
632
        $this->assertInstanceOf('GitElephant\Objects\Diff\Diff', $this->getRepository()->getDiff($commit1));
633
        $this->addFile('test-file2');
634
        $this->getRepository()->commit('commit 2', true);
635
        $commit2 = $this->getRepository()->getCommit();
636
        $this->assertInstanceOf('GitElephant\Objects\Diff\Diff', $this->getRepository()->getDiff($commit2));
637
        $this->assertInstanceOf('GitElephant\Objects\Diff\Diff', $this->getRepository()->getDiff($commit2, $commit1));
638
        $shaHead = $this->getRepository()->getCommit();
639
        $this->assertInstanceOf('GitElephant\Objects\Diff\Diff', $diff = $this->getRepository()->getDiff($shaHead));
640
    }
641
642
    /**
643
     * testCloneFrom
644
     */
645
    public function testCloneFrom()
646
    {
647
        $this->initRepository(null, 0);
648
        $this->initRepository(null, 1);
649
        $remote = $this->getRepository(0);
650
        $remote->init();
651
        $this->addFile('test', null, null, $remote);
652
        $remote->commit('test', true);
653
        $local = $this->getRepository(1);
654
        $local->cloneFrom($remote->getPath(), '.');
655
        $commit = $local->getCommit();
656
        $this->assertEquals($remote->getCommit()->getSha(), $commit->getSha());
657
        $this->assertEquals($remote->getCommit()->getMessage(), $commit->getMessage());
658
    }
659
660
    /**
661
     * testOutputContent
662
     */
663
    public function testOutputContent()
664
    {
665
        $this->initRepository();
666
        $this->getRepository()->init();
667
        $this->addFile('file1', null, 'file content');
668
        $this->getRepository()->commit('first commit', true);
669
        $branch = $this->getRepository()->getBranch('master');
670
        $tree = $this->getRepository()->getTree($branch, 'file1');
0 ignored issues
show
It seems like $branch defined by $this->getRepository()->getBranch('master') on line 669 can be null; however, GitElephant\Repository::getTree() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
671
        $treeObject = $tree->getBlob();
672
        $this->assertEquals(array('file content'), $this->getRepository()->outputContent($treeObject, $branch));
0 ignored issues
show
It seems like $branch defined by $this->getRepository()->getBranch('master') on line 669 can be null; however, GitElephant\Repository::outputContent() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
673
    }
674
675
    /**
676
     * testMove
677
     */
678
    public function testMove()
679
    {
680
        $this->getRepository()->init();
681
        $this->addFile('foo');
682
        $this->getRepository()->commit('commit 1', true);
683
        $this->getRepository()->move('foo', 'bar');
684
        $status = $this->getRepository()->getStatusOutput();
685
686
        $this->assertRegExp('/(.*):    foo -> bar/', $status[4]);
687
    }
688
689
    /**
690
     * testRemove
691
     */
692
    public function testRemove()
693
    {
694
        $this->getRepository()->init();
695
        $this->addFile('foo');
696
        $this->getRepository()->commit('commit 1', true);
697
        $this->getRepository()->remove('foo');
698
        $status = $this->getRepository()->getStatusOutput();
699
700
        $this->assertRegExp('/(.*):    foo/', $status[4]);
701
    }
702
703
    /**
704
     * testCountCommits
705
     */
706
    public function testCountCommits()
707
    {
708
        $this->getRepository()->init();
709
        $this->addFile('foo');
710
        $this->getRepository()->commit('commit 1', true);
711
        $this->assertEquals(1, $this->getRepository()->countCommits());
712
        $this->addFile('foo2');
713
        $this->getRepository()->commit('commit 2', true);
714
        $this->assertEquals(2, $this->getRepository()->countCommits());
715
        $this->getRepository()->createBranch('new-branch');
716
        $this->getRepository()->checkout('new-branch');
717
        $this->assertEquals(2, $this->getRepository()->countCommits());
718
        $this->addFile('bar');
719
        $this->getRepository()->commit('commit 3', true);
720
        $this->assertEquals(3, $this->getRepository()->countCommits());
721
        $this->getRepository()->checkout('master');
722
        $this->assertEquals(2, $this->getRepository()->countCommits());
723
    }
724
725
    /**
726
     * testHumanishName
727
     */
728
    public function testHumanishName()
729
    {
730
        $this->initRepository('test-dir');
731
        $this->assertEquals('test-dir', $this->getRepository()->getHumanishName());
732
    }
733
734
    /**
735
     * testCreateFromRemote
736
     *
737
     * @return null
738
     */
739
    public function testCreateFromRemote()
740
    {
741
        $this->initRepository(null, 0);
742
        $remote = $this->getRepository(0);
743
        $remote->init();
744
        $this->addFile('test', null, null, $remote);
745
        $remote->commit('test', true);
746
        $remote->createBranch('develop');
747
748
        $repo = Repository::createFromRemote($remote->getPath());
749
        $this->assertInstanceOf('GitElephant\Repository', $repo);
750
        $this->assertGreaterThanOrEqual(2, $repo->getBranches());
751
        $branches = $repo->getBranches();
752
        $branchesName = array_map(
753
            function (Branch $b) {
754
                return $b->getName();
755
            },
756
            $branches
757
        );
758
        $this->assertContains('master', $branchesName);
759
        $this->assertContains('develop', $branchesName);
760
    }
761
762
    /**
763
     * testAddRemote
764
     */
765
    public function testRemote()
766
    {
767
        $this->initRepository(null, 0);
768
        $remote = $this->getRepository(0);
769
        $remote->init(true);
770
        $this->initRepository();
771
        $this->repository->init();
772
        $this->repository->addRemote('github', $remote->getPath());
773
        $this->assertInstanceOf('GitElephant\Objects\Remote', $this->repository->getRemote('github'));
774
        $this->repository->addRemote('github2', $remote->getPath());
775
        $this->assertCount(2, $this->repository->getRemotes());
776
    }
777
778
    /**
779
     * testFetch, git branch -a should find the branch
780
     */
781
    public function testFetch()
782
    {
783
        $this->initRepository(null, 0);
784
        $this->initRepository(null, 1);
785
        $r1 = $this->getRepository(0);
786
        $r1->init();
787
        $this->addFile('test1', null, null, $r1);
788
        $r1->commit('test commit', true);
789
        $r1->createBranch('tag-test');
790
        $this->addFile('test2', null, null, $r1);
791
        $r1->commit('another test commit', true);
792
        $r1->createTag('test-tag');
793
        $r2 = $this->getRepository(1);
794
        $r2->init();
795
        $r2->addRemote('origin', $r1->getPath());
796
        $this->assertEmpty($r2->getBranches(true, true));
797
        $r2->fetch();
798
        $this->assertNotEmpty($r2->getBranches(true, true));
799
        $r2->fetch(null, null, true);
800
        $this->assertNotNull($r2->getTag('test-tag'));
801
    }
802
803
    /**
804
     * test pull
805
     */
806
    public function testPull()
807
    {
808
        $this->initRepository(null, 0);
809
        $this->initRepository(null, 1);
810
        $r1 = $this->getRepository(0);
811
        $r1->init();
812
        $this->addFile('test1', null, null, $r1);
813
        $r1->commit('test commit', true);
814
        $r2 = $this->getRepository(1);
815
        $r2->init();
816
        $r2->addRemote('origin', $r1->getPath());
817
        $r2->pull('origin', 'master');
818
        $this->assertEquals('test commit', $r2->getLog()->last()->getMessage());
819
        $this->assertEquals($r1->getMainBranch()->getSha(), $r2->getLog()->last()->getSha());
820
    }
821
822
    /**
823
     * test pull
824
     */
825
    public function testPush()
826
    {
827
        $this->initRepository(null, 0);
828
        $this->initRepository(null, 1);
829
        $this->initRepository(null, 2);
830
        // commit on r1
831
        $r1 = $this->getRepository(0);
832
        $r1->init();
833
        $this->addFile('test1', null, null, $r1);
834
        $r1->commit('test commit', true);
835
        // push from r1 to r2
836
        $r2 = $this->getRepository(1);
837
        $r2->init(true);
838
        $r1->addRemote('origin', $r2->getPath());
839
        $r1->push('origin', 'master');
840
        // pull from r2 to r3 should get the same result
841
        $r3 = $this->getRepository(2);
842
        $r3->init();
843
        $r3->addRemote('origin', $r2->getPath());
844
        $r3->pull('origin', 'master');
845
846
        $this->assertEquals('test commit', $r3->getLog()->last()->getMessage());
847
        $this->assertEquals($r1->getMainBranch()->getSha(), $r3->getLog()->last()->getSha());
848
    }
849
850
    public function testRevParse()
851
    {
852
        $this->initRepository(null, 0);
853
        $r = $this->getRepository(0);
854
        $r->init();
855
        $this->addFile('test1', null, null, $r);
856
        $r->commit('test commit', true);
857
        $master = $r->getBranch('master');
858
        $revParse = $r->revParse($master, array());
859
        $this->assertEquals($master->getSha(), $revParse[0]);
860
    }
861
862
    public function testIsBare()
863
    {
864
        $this->initRepository(null, 0);
865
        $r = $this->getRepository(0);
866
        $r->init();
867
868
        $this->assertEquals(false, $r->isBare());
869
870
        $this->initRepository(null, 1);
871
        $r = $this->getRepository(1);
872
        $r->init(true);
873
874
        $this->assertEquals(true, $r->isBare());
875
876
    }
877
878
    /**
879
     * test add, remove and get global configs
880
     *
881
     * @covers GitElephant\Repository::addGlobalConfig
882
     * @covers GitElephant\Repository::getGlobalConfigs
883
     * @covers GitElephant\Repository::removeGlobalConfig
884
     */
885
    public function testGlobalConfigs()
886
    {
887
        $repo = $this->getRepository();
888
889
        $configs = array(
890
            'test1' => true,
891
            'test2' => 1,
892
            'test3' => 'value',
893
        );
894
        $this->assertEmpty($repo->getGlobalConfigs());
895
896
        foreach ($configs as $configName => $configValue) {
897
            $repo->addGlobalConfig($configName, $configValue);
898
        }
899
        $this->assertSame($configs, $repo->getGlobalConfigs());
900
901
        foreach ($configs as $configName => $configValue) {
902
            $repo->removeGlobalConfig($configName, $configValue);
903
        }
904
        $this->assertEmpty($repo->getGlobalConfigs());
905
    }
906
907
    /**
908
     * test add, remove and get global options
909
     *
910
     * @covers GitElephant\Repository::addGlobalOption
911
     * @covers GitElephant\Repository::getGlobalOptions
912
     * @covers GitElephant\Repository::removeGlobalOption
913
     */
914
    public function testGlobalOptions()
915
    {
916
        $repo = $this->getRepository();
917
918
        $options = array(
919
            'test1' => true,
920
            'test2' => 1,
921
            'test3' => 'value',
922
        );
923
        $this->assertEmpty($repo->getGlobalOptions());
924
925
        foreach ($options as $configName => $configValue) {
926
            $repo->addGlobalOption($configName, $configValue);
927
        }
928
        $this->assertSame($options, $repo->getGlobalOptions());
929
930
        foreach ($options as $configName => $configValue) {
931
            $repo->removeGlobalOption($configName, $configValue);
932
        }
933
        $this->assertEmpty($repo->getGlobalOptions());
934
    }
935
936
    /**
937
     * test add, remove and get global command arguments
938
     *
939
     * @covers GitElephant\Repository::addGlobalCommandArgument
940
     * @covers GitElephant\Repository::getGlobalCommandArguments
941
     * @covers GitElephant\Repository::removeGlobalCommandArgument
942
     */
943
    public function testGlobalCommandArguments()
944
    {
945
        $repo = $this->getRepository();
946
947
        $args = array(
948
            true,
949
            1,
950
            'value',
951
        );
952
        $this->assertEmpty($repo->getGlobalCommandArguments());
953
954
        foreach ($args as $configValue) {
955
            $repo->addGlobalCommandArgument($configValue);
956
        }
957
        $this->assertSame($args, $repo->getGlobalCommandArguments());
958
959
        foreach ($args as $configValue) {
960
            $repo->removeGlobalCommandArgument($configValue);
961
        }
962
        $this->assertEmpty($repo->getGlobalCommandArguments());
963
    }
964
}
965