Skip to content

Clocks

Dependency injection

A Clock should be treated as a singleton and instanciated once in your program and then passed as argument everywhere you need it in your program.

Live

This is the clock you should use in your programs. By default it's set to the UTC timezone (no matter the configuration of your machine).

To access the current time you would do:

use Innmind\TimeContinuum\{
    Clock,
    PointInTime,
};

$clock = Clock::live();
$point = $clock->now(); // instance of PointInTime
echo $point->toString(); // prints something like 2024-11-24T12:34:25+00:00

And to build a PointInTime back from a string:

use Innmind\TimeContinuum\{
    Clock,
    Format,
    PointInTime,
};
use Innmind\Immutable\Maybe;

$time = '2024-11-24T12:34:25+00:00';

$clock = Clock::live();
$at = $clock->at($time, Format::iso8601()); // instance of Maybe<PointInTime>
$point = $at->match(
    static fn(PointInTime $point) => $point,
    static fn() => null,
);

The at method returns a Maybe monad that may contain a PointInTime. This is in case the $time variable contains a value that doesn't correspond to the specified format (here ISO8601).

This means that the $point variable here is an instance of PointInTime because the $time value is valid. If it's invalid then $point is null.

Logger

This clock will create a log everytime you call ->now() or ->at().

To build this clock you need another clock (typically a live one) and a PSR logger:

use Innmind\TimeContinuum\Clock;
use Psr\Log\LoggerInterface;

$clock = Clock::logger(
    Clock::live(),
    /* any instance of LoggerInterface (1) */
);
  1. Like monolog for example.

You can then use $clock like any other clock.

Frozen

This clock is only useful when testing your program. It allows to specify the point in time at which your programs run.

This way you can test your program for special scenarii like a leap year, daylight saving time and so on...

use Innmind\TimeContinuum\{
    Clock,
    Format,
};

$clock = Clock::live()
    ->at('2024-11-24T12:34:25+00:00', Format::iso8601())
    ->match(
        Clock::frozen(...),
        static fn() => throw new \LogicException('Specify a valid date'),
    );
Warning

Bear in mind that $clock->now() will always return the same object. This means that if your program rely on calculating an elapsed period it will always return 0. If run in a loop you may end up with an inifinite one.