On the pitfalls of date validation with the Zend Framework

I’m writing this post as a warning for people using Zend_Date to validate dates, either as a standalone or as a validator in a chain. I’ve been using Zend_Validate_Date validator, which uses the Zend_Date::isDate() method internally, for a while now – mainly for form processing.

I’ve recently completed a project where a very bizarre bug would occur on some machines, and I wasn’t able to reproduce it myself on any test machine that I tried. The bug manifested in a calendar system we built for the project, and in certain situations form submissions would not pass the date validation through Zend_Validate_Date, despite using the exact same input that was passing on the test machines.

After bringing in one of the “affected” machines for testing, I used the process of elimination to determine the problem originates in the Zend_Date::isDate() method, which has different behavior on different machines.

Zend_Date tries to validate dates according to a given format (with a default fallback). The dangerous behavior is that it tries to convert the given format to a localized format using Zend_Locale. Zend_Locale attempts to detect automatically the locale of the requesting client, and it appears that on the machines that were exhibiting the bug, a different locale was determined than those I was testing it on.

Despite trying to validate a non-localized format (to be exact, the MySQL timestamp format – YYYY-MM-dd HH:mm:sss), it was being converted on the affected machine sdue to the auto-detection by Zend_Locale (on a side note – it was happening on Internet Explorer 8 on Windows 7). To avoid this issue, I set the locale for all requests manually to en_US, since I don’t have any other use for Zend_Locale in the application. I put the following lines in the bootstrap –

$locale = new Zend_Locale('en_US');
Zend_Registry::set('Zend_Locale', $locale);

As recommended by the manual to achieve this effect.

In my opinion, the Locale should be not be auto-detected by default – it should be an opt-in feature if it affects other components behind the scenes.

To know when the next article is published, please subscribe to new articles using your Email below or follow me on Twitter.

Subscribe to Blog via Email

Enter your email address to receive notification about new posts.

  • http://www.papayasoft.com/ David Weinraub

    I was looking at that same issue just yesterday.

    I am using Zend_Form (and all its rich, creamy goodness) in a legacy-non-ZF project. As a result, the all my locales are null and the default behavior for null locales was doing what I want. So I was able to avoid the whole thing.

    But I agree with you. Consider the case of using a client-side component that allows the user to select a date and I configure that component to create a date in my expected format. I would be pretty irritated if the validation went all goofy simply because the format is invalid relative to the framework-generated locale.

    Is there no setting to disable locale processing? I confess to being a bit of a ZF n00b, especially re: locales.

    Anyway, nice post. Cheers!

  • http://www.papayasoft.com/ David Weinraub

    I was looking at that same issue just yesterday.

    I am using Zend_Form (and all its rich, creamy goodness) in a legacy-non-ZF project. As a result, the all my locales are null and the default behavior for null locales was doing what I want. So I was able to avoid the whole thing.

    But I agree with you. Consider the case of using a client-side component that allows the user to select a date and I configure that component to create a date in my expected format. I would be pretty irritated if the validation went all goofy simply because the format is invalid relative to the framework-generated locale.

    Is there no setting to disable locale processing? I confess to being a bit of a ZF n00b, especially re: locales.

    Anyway, nice post. Cheers!

  • http://www.techfounder.net Eran Galperin

    The method I suggested at the end of the post allows you to set the locale to one that you know will not change your date format (en_US)

  • http://www.techfounder.net Eran Galperin

    The method I suggested at the end of the post allows you to set the locale to one that you know will not change your date format (en_US)

  • http://www.itsaboutwebsites.com Paul

    Dates are such a ballache!

    The more I work with them the more I am convinced that our applications are going to internally work with UTC, and conversion is only done in the client. The disadvantage of this is that it would most definitely make javascript a client side requirement.

  • http://www.itsaboutwebsites.com Paul

    Dates are such a ballache!

    The more I work with them the more I am convinced that our applications are going to internally work with UTC, and conversion is only done in the client. The disadvantage of this is that it would most definitely make javascript a client side requirement.

  • http://www.mhdzaherghaibeh.name/ Mhd zaher ghaibeh

    i have had the same issue but not with the date validation but with the float validation.
    and i have solved it with the same solutions …
    so be careful …

    now am so convinced that i have to set my locale before doing any validations ..

  • http://www.mhdzaherghaibeh.name/ Mhd zaher ghaibeh

    i have had the same issue but not with the date validation but with the float validation.
    and i have solved it with the same solutions …
    so be careful …

    now am so convinced that i have to set my locale before doing any validations ..

  • http://twitter.com/sajbar Daniel Borg

    I had the same problem with floats, when using a danish browser, using an english browser caused the floats to validate just fine.

    my unittests failed as well, but I didn’t get any error messages, setting the locale in my bootstrap fixed this.

    Thanks for posting this