Passed
Push — master ( 7f22df...6cb86d )
by Kauri
02:52
created

PaymentsCalculator::calculatePayments()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 57
Code Lines 29

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 21
CRAP Score 3

Importance

Changes 0
Metric Value
dl 0
loc 57
ccs 21
cts 21
cp 1
rs 9.6818
c 0
b 0
f 0
cc 3
eloc 29
nc 3
nop 4
crap 3

How to fix   Long Method   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
declare(strict_types = 1);
4
5
namespace Kauri\Loan;
6
7
8
class PaymentsCalculator implements PaymentsCalculatorInterface
9
{
10
    /**
11
     * @var PaymentAmountCalculatorInterface
12
     */
13
    private $paymentAmountCalculator;
14
    /**
15
     * @var InterestAmountCalculatorInterface
16
     */
17
    private $interestAmountCalculator;
18
19
    /**
20
     * PaymentsCalculator constructor.
21
     * @param PaymentAmountCalculatorInterface $paymentAmountCalculator
22
     * @param InterestAmountCalculatorInterface $interestAmountCalculator
23
     */
24 4
    public function __construct(
25
        PaymentAmountCalculatorInterface $paymentAmountCalculator,
26
        InterestAmountCalculatorInterface $interestAmountCalculator
27
    ) {
28 4
        $this->paymentAmountCalculator = $paymentAmountCalculator;
29 4
        $this->interestAmountCalculator = $interestAmountCalculator;
30 4
    }
31
32
    /**
33
     * @param PaymentPeriodsInterface $paymentPeriods
34
     * @param float $amountOfPrincipal
35
     * @param float $yearlyInterestRate
36
     * @param int $calculationMode
37
     * @return array
38
     */
39 4
    public function calculatePayments(
40
        PaymentPeriodsInterface $paymentPeriods,
41
        float $amountOfPrincipal,
42
        float $yearlyInterestRate,
43
        int $calculationMode
44
    ): array {
45 4
        $payments = array();
46
47 4
        $numberOfPayments = $paymentPeriods->getNoOfPeriods();
48 4
        $principalLeft = $amountOfPrincipal;
49
50 4
        foreach ($paymentPeriods->getPeriods() as $key => $period) {
51 4
            $ratePerPeriod = $paymentPeriods->getRatePerPeriod($period, $yearlyInterestRate, $calculationMode);
52 4
            $numberOfPeriods = $paymentPeriods->getNumberOfRemainingPeriods($period, $calculationMode);
53
54
            /**
55
             * Calculate payment amount
56
             */
57 4
            $paymentAmount = $this->paymentAmountCalculator->getPaymentAmount($principalLeft, $ratePerPeriod,
58
                $numberOfPeriods);
59
60
            /**
61
             * Calculate interest part
62
             */
63 4
            $interest = $this->interestAmountCalculator->getInterestAmount($principalLeft, $ratePerPeriod);
64
65
            /**
66
             * Calculate principal part
67
             */
68 4
            if ($key < $numberOfPayments) {
69 3
                $principal = $paymentAmount - $interest;
70
            } else {
71 4
                $principal = $principalLeft;
72
            }
73
74
            /**
75
             * Calculate balance left
76
             */
77 4
            $principalLeft = round($principalLeft - $principal, 2);
78
79
            /**
80
             * Compose payment data
81
             */
82
            $paymentData = array(
83 4
                'sequence_no' => $key,
84 4
                'payment' => $interest + $principal,
85 4
                'principal' => $principal,
86 4
                'interest' => $interest,
87 4
                'principal_left' => $principalLeft,
88 4
                'period' => $period
89
            );
90
91 4
            $payments[$key] = $paymentData;
92
        }
93
94 4
        return $payments;
95
    }
96
}
97