Passed
Pull Request — master (#2)
by Kauri
02:48
created

PaymentPeriodsTest::testRemainingPeriod()   A

Complexity

Conditions 3
Paths 4

Size

Total Lines 22
Code Lines 13

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 22
rs 9.2
c 0
b 0
f 0
cc 3
eloc 13
nc 4
nop 2
1
<?php
2
3
namespace Kauri\Loan\Test;
4
5
6
use Kauri\Loan\PaymentPeriods;
7
use Kauri\Loan\Period;
8
use PHPUnit\Framework\TestCase;
9
10
11
class PaymentPeriodsTest extends TestCase
12
{
13
    /**
14
     * @dataProvider periodsData
15
     * @param $averagePeriodLength
16
     * @param $paymentPeriods
17
     */
18
    public function testPaymentPeriods($averagePeriodLength, $paymentPeriods)
19
    {
20
        $periodsCollection = new PaymentPeriods($averagePeriodLength);
21
        $noOfPayments = count($paymentPeriods);
22
        $totalLength = 0;
23
        $periodLength = 0;
24
25
        $this->assertEquals(0, $periodsCollection->getNoOfPeriods());
26
        $this->assertTrue(empty($periodsCollection->getPeriods()));
27
28
        foreach ($paymentPeriods as $periodLength) {
29
            $periodMock = $this->getMockPeriod($periodLength);
30
            $periodsCollection->add($periodMock);
31
            $totalLength = $totalLength + $periodLength;
32
        }
33
34
        $periods = $periodsCollection->getPeriods();
35
        $period = current($periods);
36
        $length = $period->getLength();
37
38
        $this->assertEquals($noOfPayments, $periodsCollection->getNoOfPeriods());
39
        $this->assertTrue(!empty($periodsCollection->getPeriods()));
40
41
        $this->assertEquals($totalLength / $length,
42
            $periodsCollection->getNumberOfRemainingPeriods($period, $periodsCollection::CALCULATION_TYPE_EXACT));
43
        $this->assertEquals($noOfPayments,
44
            $periodsCollection->getNumberOfRemainingPeriods($period, $periodsCollection::CALCULATION_TYPE_EXACT_INTEREST));
45
        $this->assertEquals($noOfPayments,
46
            $periodsCollection->getNumberOfRemainingPeriods($period, $periodsCollection::CALCULATION_TYPE_ANNUITY));
47
48
        $this->assertEquals($length,
49
            $periodsCollection->getRatePerPeriod($period, 360,
50
                $periodsCollection::CALCULATION_TYPE_EXACT));
51
        $this->assertEquals($length,
52
            $periodsCollection->getRatePerPeriod($period, 360,
53
                $periodsCollection::CALCULATION_TYPE_EXACT_INTEREST));
54
        $this->assertEquals($averagePeriodLength,
55
            $periodsCollection->getRatePerPeriod($period, 360,
56
                $periodsCollection::CALCULATION_TYPE_ANNUITY));
57
    }
58
59
    /**
60
     * @dataProvider periodsData
61
     * @param int $averagePeriodLength
62
     * @param array $paymentPeriods
63
     */
64
    public function testRemainingPeriod(int $averagePeriodLength, array $paymentPeriods)
65
    {
66
        $periodsCollection = new PaymentPeriods($averagePeriodLength);
67
68
        foreach ($paymentPeriods as $periodLength) {
69
            $periodMock = $this->getMockPeriod($periodLength);
70
            $periodsCollection->add($periodMock);
71
        }
72
73
        $reversedPeriods = array_reverse($paymentPeriods);
74
75
        $periods = $periodsCollection->getPeriods();
76
77
        foreach ($periods as $p) {
78
            array_pop($reversedPeriods);
79
            $exactRemainingPeriodsLength = $periodsCollection->getExactRemainingPeriodsLength($p);
80
            $averageRemainingPeriodsLength = $periodsCollection->getAverageRemainingPeriodsLength($p);
81
82
            $this->assertEquals($exactRemainingPeriodsLength, array_sum($reversedPeriods));
83
            $this->assertEquals($averageRemainingPeriodsLength, $averagePeriodLength * count($reversedPeriods));
84
        }
85
    }
86
87
    public function periodsData()
88
    {
89
        return [
90
            [7, [6, 5, 3, 9]],
91
            [30, [29, 30, 31, 30, 28]]
92
        ];
93
    }
94
95
    /**
96
     * @expectedException \Exception
97
     */
98
    public function testRatePerPeriodException()
99
    {
100
        $periodsCollection = new PaymentPeriods(1);
101
        $periodsCollection->getRatePerPeriod($this->getMockPeriod(3), 10, 10);
102
    }
103
104
    /**
105
     * @expectedException \Exception
106
     */
107
    public function testNumberOfPeriodsException()
108
    {
109
        $periodsCollection = new PaymentPeriods(1);
110
        $periodsCollection->getNumberOfRemainingPeriods($this->getMockPeriod(3), 10);
111
    }
112
113
    private function getMockPeriod($length)
114
    {
115
        $stub = $this->getMockBuilder(Period::class)
116
            ->disableOriginalConstructor()
117
            ->setMethods(['getLength'])
118
            ->getMock();
119
120
        $stub->method('getLength')
121
            ->willReturn($length);
122
123
        return $stub;
124
    }
125
126
}
127