digital-craftsman/date-time-precision
Thin PHP value objects for precise date/time concepts: Moment (UTC-backed) plus Time, Date, Month, Year, Day, Weekday and collections. Avoid misleading DateTime comparisons, handle timezone-safe modifications (DST), with Symfony normalizers and Doctrine types.
DateTime for non-moment-specific operations (e.g., comparing times, dates, or months). Its value-object approach (Moment, Time, Date, Month, Year) aligns well with Domain-Driven Design (DDD) and Laravel’s Eloquent/Doctrine integration, reducing boilerplate and improving type safety.Moment objects while allowing timezone-aware modifications for business logic (e.g., modifyInTimeZone). This is highly compatible with Laravel’s default timezone handling (e.g., config('app.timezone')) but requires explicit opt-in for timezone-aware operations.Moment and its components prevents side effects, which is a best practice for Laravel services and repositories. This contrasts with PHP’s mutable DateTime, reducing bugs in stateful operations.HttpKernel and DependencyInjection are not required). The package’s Doctrine DBAL types and Symfony normalizers are optional but valuable for:
Moment, Date, etc., enable direct ORM mapping (e.g., in Laravel’s Eloquent models via hasOne/belongsTo with custom accessors).Serializer, but Laravel’s Fractal/JSONAPI can adapt via custom transformers.Moment can wrap Carbon instances for consistency. A bridge adapter (e.g., CarbonMoment) would be needed for seamless interoperability.Clock interface (with SystemClock/FrozenClock) enables time-freezing for tests, which is already a Laravel pattern (e.g., Carbon::setTestNow()). This can be extended to support the package’s Clock.Moment operations into SQL (e.g., whereDate('created_at', '>', $date)).0.14.* in composer.json to avoid surprises.Day/Days in v0.14.0) to isolate changes.Moment objects.DateTime, adding a thin abstraction layer. Benchmarking is needed for high-frequency operations (e.g., bulk inserts), but the overhead is likely negligible for most use cases.Mockery) may need adjustments for Clock/Moment interactions.Moment replace all DateTime/Carbon instances, or only for domain-specific logic (e.g., booking systems)?now(), Carbon::parse())?DateTime code coexist with Moment (e.g., via adapters)?travel()) adapt to the Clock interface?FrozenClock replace Laravel’s Carbon::setTestNow()?timestamp/date columns need migration to use the package’s Doctrine types?DB::raw) interact with Moment objects?Moment overhead could impact latency?DateTime/Carbon for domain-specific date logic (e.g., business hours, scheduling).Serializer).digital-craftsman/self-aware-normalizers directly in Laravel via spatie/fractal or laravel/serializable.Carbon::setTestNow() with FrozenClock for consistent time freezing.Mockery to stub Moment methods in unit tests.Carbon with Moment in domain services.CarbonMoment) to bridge existing DateTime code.Moment serialization.Rector for automated DateTime→Moment refactoring.PHPStan to enforce Moment usage in new code.timestamp fields with Moment types via database migrations (if using Doctrine types).Fractal/JSONAPI for consistent serialization.Carbon::now() with SystemClock::now().Moment as the default date type in the application.| Laravel Component | Compatibility | Workaround |
|---|---|---|
| Eloquent | Low (Doctrine types not natively supported) | Custom accessors or Eloquent attributes. |
| Query Builder | Medium (requires SQL translation) | Use Moment::toDateTime() for raw queries. |
| Carbon | High (via adapters) | CarbonMoment wrapper class. |
| API Serialization | Medium (Symfony normalizers not native) | Use spatie/fractal or custom JSON serialization. |
| Testing (Pest/PhpUnit) | High (Clock interface supports time freezing) | Replace Carbon::setTestNow() with FrozenClock. |
| Cache (Redis/Memcached) | High (serialization works with normalizers) | Ensure Moment objects are serializable. |
| Queues/Jobs | High (immutability prevents side effects) | Use Moment in job payloads. |
composer require digital-craftsman/date-time-precision:0.14.*.Clock binding to Laravel’s service container:
$app->bind(Clock::class, function () {
return app()->environment('testing')
? new FrozenClock()
: new SystemClock();
});
DateTime/Carbon with Moment in services/repositories.// Before
$now = Carbon
How can I help you explore Laravel packages today?