Re: [PHP-DEV] Add ISO 8601 date format constant with millisecond precision
Andreas Heigl <[email protected]>
| Newsgroups | gmane.comp.php.devel |
|---|---|
| Message-ID | <[email protected]> |
Hey Théo
On 29.08.26 18:04, Théo Attali wrote:
> Hi Andreas,
>
> Thank you for your feedback.
>
> I agree that a format constant containing a literal Z is not ideal because
> the format string cannot enforce UTC. A userland formatter is safer because
> it can normalize the value before formatting it.
>
> After considering this, I think an instance method may be a better fit than
> a new format constant:
>
> $date->toISOString();
>
> The method could normalize the instant to UTC and return exactly:
>
> 1970-01-01T00:00:00.000Z
>
> It would not modify the original object, which is particularly important for
> DateTimeImmutable.
>
> I also found that Carbon provides:
>
> $date->toIso8601ZuluString('millisecond');
>
> However, that requires an external dependency. My motivation is to provide
> a dependency-free way to produce a common ISO 8601 UTC representation used
> when exchanging timestamps between PHP, JavaScript, Java, Go, and other
> ecosystems.
>
> I searched for an existing PHP issue or RFC proposing this exact method but
> found only the older, inactive DateTime::__toString() RFC, which addressed
> a different problem.
>
> Would you consider a UTC-normalizing instance method a more appropriate
> direction for this issue than adding a format constant?
Well... PHP already *has* a dependency-free way to format any
datetime-object into an ISO string:
echo $anyDateTimeImmutable
->setTimezone(new DateTimeZone('UTC'))
->format('Y-m-d\\TH:i:s.vP');
If you want to avoid having to write that string all the time, feel free
to do something like
Interface IsoDateTime
{
const WITH_MILLISECONDS = 'Y-m-d\\TH:i:s.vP';
const JUST_SECONDS = 'Y-m-d\\TH:i:sP';
}
and then call
echo $anyDateTimeImmutable
->setTimezone(new DateTimeZone('UTC'))
->format(IsoDateTimeInterface::WITH_MILLISECONDS);
That works since PHP5.3
Anything else is adding convenience at a cost.
And for me (but I am just one person here on the list) that cost
(limited availability to older versions, increasingly polluted
constants, very specific use-case, possibly broken output due to wrong
timezone) outweighs the benfits.
Just my 0.02€
Cheers
Andreas
>
> Best regards,
>
> Théo Attali
>
> El sáb, 29 ago 2026 a las 12:36, Andreas Heigl (<[email protected]>)
> escribió:
>
>> Hey Théo
>>
>> On 29.08.26 11:47, Théo Attali wrote:
>>> Hi !
>>>
>>> Sorry derick for the duplicated email but I was not registered.
>>>
>>> This is my first contribution, so I would appreciate any help on the
>>> proposal and on following the project's contribution process.
>>>
>>> I opened issue #23491 for a possible addition to ext/date:
>>>
>>> https://github.com/php/php-src/issues/23491
>>>
>>> I would appreciate feedback before preparing an implementation.
>>>
>>> PHP currently provides DATE_RFC3339_EXTENDED, which includes millisecond
>>> precision. For a UTC DateTime, it produces:
>>>
>>> 1970-01-01T00:00:00.000+00:00
>>>
>>> Some applications need the equivalent representation with the ISO 8601
>> UTC
>>> designator Z:
>>>
>>> 1970-01-01T00:00:00.000Z
>>>
>>> This is also the format produced by JavaScript's
>>> Date.prototype.toISOString():
>>>
>>> new Date(0).toISOString();
>>> // "1970-01-01T00:00:00.000Z"
>>>
>>> Would a predefined format for this representation be appropriate for
>>> ext/date?
>>>
>>> One possible API would be:
>>>
>>> DATE_ISO8601_MILLISECONDS_UTC
>>> DateTimeInterface::ISO8601_MILLISECONDS_UTC
>>>
>>> with the format string:
>>>
>>> "Y-m-d\\TH:i:s.v\\Z"
>>>
>>> For example:
>>>
>>> $date = new DateTimeImmutable('@0');
>>> echo $date->setTimezone(new DateTimeZone('UTC'))
>>> ->format(DATE_ISO8601_MILLISECONDS_UTC);
>>>
>>> // 1970-01-01T00:00:00.000Z
>>>
>>> The name and API shape are open for discussion. Another option would be
>> an
>>> offset-preserving format:
>>>
>>> DATE_ISO8601_MILLISECONDS
>>> DateTimeInterface::ISO8601_MILLISECONDS
>>>
>>> using:
>>>
>>> "Y-m-d\\TH:i:s.vP"
>>>
>>> I understand that date format constants only define formatting; they do
>> not
>>> change the timezone of the DateTime object.
>>> A format containing a literal Z would therefore require the caller to
>>> normalize the object to UTC first.
>>>
>>> For context, issue #14593 discusses the interpretation of the Z suffix
>> when
>>> parsing DateTime values:
>>>
>>> https://github.com/php/php-src/issues/14593
>>>
>>> That issue concerns parsing and timezone representation, whereas this
>>> proposal concerns predefined formatting constants.
>>>
>>> I would appreciate feedback on:
>>>
>>> 1. Whether a millisecond-precision format is useful in addition to
>>> DATE_RFC3339_EXTENDED.
>>> 2. Whether an offset-preserving format or a UTC-suffix format is
>> preferable.
>>> 3. Whether the proposed names follow the preferred ext/date convention.
>>> 4. Whether an RFC is required before implementation.
>>>
>>> Thank you,
>>>
>>> Théo Attali
>>>
>> I see some serious issues with the idea of adding the format with the
>> `\\Z` at the end as you already described. It would require a
>> prerequisite that can'T be enforced and that will therefore cause a lot
>> of confusion.
>>
>> To ease that confusion I would recommend anyone that has that explicit
>> requirement to create a Formatter - perhaps tehr eeven is one already
>> available that in essence just does something like this:
>>
>> class Formatter
>> {
>> public static function formatIso(DateTimeImmutable $date): string
>> {
>> return $date->setTimezone(new
>> DateTimeZone('UTC'))->format('Y-m-d\\TH:i:s.vP');
>> }
>> }
>>
>> Maintaining such a set of Formatters in Userland seems to be much easier
>> than adding that in the PHP-Src. It would also make the formatter
>> available to ALL PHP-Versions that have a DateTimeImmutable object and
>> not only PHP8.6/8.7 onwards.
>>
>> From my side I would by now not add any more constants to the
>> PHP-Source as they will not be available to earler versions. And I say
>> that as the person that added the _EXTENDED constants...
>>
>> By now I would create a formatter in userland and promote that for usage
>> as it's a small library that can be used by *any* PHP-Version that needs
>> it.
>>
>> My 0.02€
>>
>> Cheers
>>
>> Andreas
>> --
>> ,,,
>> (o o)
>> +---------------------------------------------------------ooO-(_)-Ooo-+
>> | Andreas Heigl |
>> | mailto:[email protected] N 50°22'59.5" E 08°23'58" |
>> | https://andreas.heigl.org |
>> +---------------------------------------------------------------------+
>> | https://hei.gl/appointmentwithandreas |
>> +---------------------------------------------------------------------+
>> | GPG-Key: https://hei.gl/keyandreasheiglorg |
>> +---------------------------------------------------------------------+
>>
>>
>
--
,,,
(o o)
+---------------------------------------------------------ooO-(_)-Ooo-+
| Andreas Heigl |
| mailto:[email protected] N 50°22'59.5" E 08°23'58" |
| https://andreas.heigl.org |
+---------------------------------------------------------------------+
| https://hei.gl/appointmentwithandreas |
+---------------------------------------------------------------------+
| GPG-Key: https://hei.gl/keyandreasheiglorg |
+---------------------------------------------------------------------+