Skip to content

[Validator] Timezone passing to IntlDateFormatter breaks when using ISO8601 zulu times #33901

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
sjdaws opened this issue Oct 8, 2019 · 0 comments

Comments

@sjdaws
Copy link

sjdaws commented Oct 8, 2019

Symfony version(s) affected: 4.3.5

Description
The validator update in 4.3.5 passes the timezone from the DateTime object to IntlDateFormatter which breaks when using zulu timestamps (YYYY-MM-DDTHH:MM:SSZ).

How to reproduce
Extend constraint validator and attempt to validate a zulu timestamp as PRETTY_DATE:

<?php

use \DateTime;
use \Symfony\Component\Validator\Constraint;
use \Symfony\Component\Validator\ConstraintValidator;

class TestValidator extends ConstraintValidator
{
    public function __construct()
    {
        $dateTime = new DateTime('2022-12-12T08:30:42Z');

        // This will throw a fatal error
        $this->formatValue($dateTime, ConstraintValidator::PRETTY_DATE);
    }

    public function validate($value, Constraint $constraint)
    {
    }
}

Possible Solution
Check the validity of the timezone before passing it to IntlDateFormatter.

Additional context
Error returned:

IntlException : datefmt_create: time zone id 'Z' extracted from ext/date DateTimeZone not recognized: U_ILLEGAL_ARGUMENT_ERROR
@javiereguiluz javiereguiluz added this to the 4.3 milestone Oct 8, 2019
nicolas-grekas added a commit that referenced this issue Dec 13, 2019
…zones (fancyweb)

This PR was merged into the 3.4 branch.

Discussion
----------

[Validator][ConstraintValidator] Safe fail on invalid timezones

Co-authored-by: Scott Dawson <scott@loyaltycorp.com.au>

| Q             | A
| ------------- | ---
| Branch?       | 3.4
| Bug fix?      | yes
| New feature?  | no
| Deprecations? | no
| Tickets       | #33901
| License       | MIT
| Doc PR        |

Alternative to #33902.

I will explain why I think it is better this way:

1. We set the timezone with the setter because it's 100% safe, it never fails. It fall backs to the default timezone if the provided timezone is not supported (as if we passed null, so the same behavior that always existed). We are therefore compatible with all edge cases.
2. We don't validate the timezone with `\DateTimeZone::listIdentifiers()`. It only returns full identifiers like "Europe/Paris" but it doesn't take into account "numeric" identifiers such as "+08:00" which are perfectly valid. I added a test case to ensure we stay valid with this case. + some invalid identifiers for the native `\IntlDateFormatter` are valid with the polyfill that uses `\DateTimeZone` (eg : `X`). I don't think we can validate anything safely that will work reliably on both implementations.

Commits
-------

3b1b994 [Validator][ConstraintValidator] Safe fail on invalid timezones
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

4 participants