RewindableDateTimeClock   A
last analyzed

Complexity

Total Complexity 8

Size/Duplication

Total Lines 45
Duplicated Lines 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 19
c 1
b 0
f 0
dl 0
loc 45
rs 10
wmc 8

6 Methods

Rating   Name   Duplication   Size   Complexity  
A create() 0 3 1
A rewind() 0 5 1
A __construct() 0 3 1
A using() 0 3 1
A now() 0 10 3
A fastForward() 0 5 1
1
<?php declare(strict_types=1);
2
3
namespace Stratadox\Clock;
4
5
use DateInterval;
6
use DateTimeInterface;
7
8
/**
9
 * RewindableDateTimeClock. This clock can be rewinded- or fast-forwarded as
10
 * needed. This implementation is immutable; alterations to the time offset
11
 * apply only to the returned copy of the clock, the original instance is not
12
 * affected.
13
 *
14
 * @author Stratadox
15
 */
16
final class RewindableDateTimeClock implements RewindableClock
17
{
18
    private $clock;
19
    private $rewinds = [];
20
    private $fastForwards = [];
21
22
    private function __construct(Clock $clock)
23
    {
24
        $this->clock = $clock;
25
    }
26
27
    public static function create(): RewindableClock
28
    {
29
        return new self(DateTimeClock::create());
30
    }
31
32
    public static function using(Clock $originalClock): RewindableClock
33
    {
34
        return new self($originalClock);
35
    }
36
37
    public function rewind(DateInterval $interval): RewindableClock
38
    {
39
        $new = clone $this;
40
        $new->rewinds[] = $interval;
41
        return $new;
42
    }
43
44
    public function fastForward(DateInterval $interval): RewindableClock
45
    {
46
        $new = clone $this;
47
        $new->fastForwards[] = $interval;
48
        return $new;
49
    }
50
51
    public function now(): DateTimeInterface
52
    {
53
        $datetime = $this->clock->now();
54
        foreach ($this->rewinds as $rewind) {
55
            $datetime = $datetime->sub($rewind);
56
        }
57
        foreach ($this->fastForwards as $fastForward) {
58
            $datetime = $datetime->add($fastForward);
59
        }
60
        return $datetime;
61
    }
62
}
63