RangeEachYear::startMonthIncludes()   A
last analyzed

Complexity

Conditions 3
Paths 3

Size

Total Lines 11
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 5
CRAP Score 3.0416

Importance

Changes 0
Metric Value
cc 3
eloc 5
nc 3
nop 1
dl 0
loc 11
ccs 5
cts 6
cp 0.8333
crap 3.0416
rs 9.4285
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Adlogix\EventScheduler\TemporalExpression;
6
7
use Adlogix\EventScheduler\ValueObject\Month;
8
use Adlogix\EventScheduler\ValueObject\MonthDay;
9
use DateTimeInterface;
10
11
/**
12
 * @author Toni Van de Voorde <[email protected]>
13
 */
14
final class RangeEachYear implements TemporalExpressionInterface
15
{
16
    /**
17
     * @var Month
18
     */
19
    protected $startMonth;
20
21
    /**
22
     * @var Month
23
     */
24
    protected $endMonth;
25
26
    /**
27
     * @var MonthDay
28
     */
29
    protected $startDay;
30
31
    /**
32
     * @var MonthDay
33
     */
34
    protected $endDay;
35
36
    /**
37
     * @param Month         $startMonth
38
     * @param Month         $endMonth
39
     * @param MonthDay|null $startDay
40
     * @param MonthDay|null $endDay
41
     */
42 6
    public function __construct(
43
        Month $startMonth,
44
        Month $endMonth,
45
        MonthDay $startDay = null,
46
        MonthDay $endDay = null
47
    ) {
48 6
        $this->startMonth = $startMonth;
49 6
        $this->endMonth = $endMonth;
50
51 6
        $this->startDay = $startDay;
52 6
        $this->endDay = $endDay;
53 6
    }
54
55
    /**
56
     * {@inheritdoc}
57
     */
58 6
    public function includes(DateTimeInterface $date): bool
59
    {
60 6
        return $this->monthsInclude($date)
61 3
            || $this->startMonthIncludes($date)
62 6
            || $this->endMonthIncludes($date);
63
    }
64
65
    /**
66
     * @param DateTimeInterface $date
67
     * @return bool
68
     */
69 6
    private function monthsInclude(DateTimeInterface $date): bool
70
    {
71 6
        $month = Month::fromDateTime($date);
72 6
        $ordinalMonth = $month->number();
73
74 6
        $ordinalStartMonth = $this->startMonth->number();
75 6
        $ordinalEndMonth = $this->endMonth->number();
76
77 6
        if ($ordinalStartMonth <= $ordinalEndMonth) {
78 5
            return ($ordinalMonth > $ordinalStartMonth && $ordinalMonth < $ordinalEndMonth);
79
        } else {
80 1
            return ($ordinalMonth > $ordinalStartMonth || $ordinalMonth < $ordinalEndMonth);
81
        }
82
    }
83
84
    /**
85
     * @param DateTimeInterface $date
86
     * @return bool
87
     */
88 3
    private function startMonthIncludes(DateTimeInterface $date): bool
89
    {
90 3
        if (!$this->startMonth->equals(Month::fromDateTime($date))) {
91 2
            return false;
92
        }
93
94 1
        if (!$this->startDay) {
95
            return true;
96
        }
97
98 1
        return $this->startDay->lte(MonthDay::fromDateTime($date));
99
    }
100
101
    /**
102
     * @param DateTimeInterface $date
103
     * @return bool
104
     */
105 3
    private function endMonthIncludes(DateTimeInterface $date): bool
106
    {
107 3
        if (!$this->endMonth->equals(Month::fromDateTime($date))) {
108 1
            return false;
109
        }
110
111 2
        if (!$this->endDay) {
112
            return true;
113
        }
114
115 2
        return $this->endDay->gte(MonthDay::fromDateTime($date));
116
    }
117
}
118