feat(services): add monday-friday working day determiner

This commit is contained in:
Ondrej Vlach 2024-08-07 12:45:05 +02:00
parent 114271d724
commit 5633ff78c6
No known key found for this signature in database
GPG Key ID: 7F141CDACEDEE2DE
3 changed files with 111 additions and 0 deletions

View File

@ -0,0 +1,37 @@
<?php
declare(strict_types=1);
namespace App\Services\WorkingDays\Date;
use App\Services\WorkingDays\WorkingDayDeterminerInterface;
/**
* Determines if a given date is a working day (Monday to Friday)
*/
class MonToFriWorkingDayDeterminer implements WorkingDayDeterminerInterface
{
public function __construct()
{
}
public function isWorkingDay(\DateTimeImmutable $date): bool
{
$weekday = $date->format('N');
return $weekday <= 5; // Monday to Friday
}
public function getWorkingDaysCount(\DateTimeImmutable $startDate, int $workingDays): int
{
$period = new \DatePeriod($startDate, new \DateInterval('P1D'), $startDate->add(new \DateInterval(sprintf('P%dD', $workingDays))));
$workingDaysCount = 0;
foreach ($period as $date) {
if ($this->isWorkingDay($date)) {
$workingDaysCount++;
}
}
return $workingDaysCount;
}
}

View File

@ -0,0 +1,26 @@
<?php
declare(strict_types=1);
namespace App\Services\WorkingDays;
/**
* Determinate if a given date is a working day.
*/
interface WorkingDayDeterminerInterface
{
/**
* Determinate if a given date is a working day.
* @param \DateTimeImmutable $date
* @return bool
*/
public function isWorkingDay(\DateTimeImmutable $date): bool;
/**
* Get working days count in a given interval.
* @param \DateTimeImmutable $startDate
* @param int $workingDays
* @return int
*/
public function getWorkingDaysCount(\DateTimeImmutable $startDate, int $workingDays): int;
}

View File

@ -0,0 +1,48 @@
<?php
declare(strict_types=1);
namespace Tests\Unit\Services\WorkingDays\Date;
use App\Services\WorkingDays\Date\MonToFriWorkingDayDeterminer;
use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\TestCase;
class MonToFriWorkingDayDeterminerTest extends TestCase
{
#[DataProvider('nonWorkingDayProvider')]
public function testIsWorkingDayWillReturnFalseForSatSan(int $day): void
{
$class = new MonToFriWorkingDayDeterminer();
$this->assertFalse($class->isWorkingDay(new \DateTimeImmutable("2024-01-0" . $day)));
}
/**
* @return array<int, array<int, int>>
*/
public static function nonWorkingDayProvider(): array
{
return [[6], [7]];
}
/**
* @return \Generator<int, array<int>>
*/
public static function workingDayProvider(): \Generator
{
for ($isNWD = 0; $isNWD <= 1; $isNWD++) {
for ($x = 1; $x <= 5; $x++) {
yield [$x];
}
}
}
#[DataProvider('workingDayProvider')]
public function testIsWorkingDayWillCallIsNWDForWorkingDaysAndReturnValue(int $day): void
{
$class = new MonToFriWorkingDayDeterminer();
$this->assertSame(true, $class->isWorkingDay(new \DateTimeImmutable("2024-01-0" . $day)));
}
}