Search code examples
phpimap

Can't parse `imap_check` date format


I'm retrieving the date using imap_check and it's returning a value like:

Fri, 21 Feb 2014 14:02:37 +0000 (GMT)

This doesn't seem to match the docs and I was expecting:

Fri, 21 Feb 2014 14:02:37 +0000

I've attempted to change my format to match the results but neither work:

//Old RFC2822 format
$date = DateTime::createFromFormat('D, d M Y H:i:s O',$dateString);

//Using timezone abbrev
$date = DateTime::createFromFormat('D, d M Y H:i:s O (T)',$dateString);

//Using timezone identifier
$date = DateTime::createFromFormat('D, d M Y H:i:s O (e)',$dateString);

However the two attempts above both return a date of false.


Solution

  • Your second attempt using (T) in parentheses looks to almost have been correct, but it will work by omitting the ():

    $d = DateTime::createFromFormat('D, d M Y H:i:s O T', 'Fri, 21 Feb 2014 14:02:37 +0000 (GMT)');
    //-----------------------------------------------^^^
    var_dump($d);
    class DateTime#3 (3) {
      public $date =>
      string(19) "2014-02-21 14:02:37"
      public $timezone_type =>
      int(2)
      public $timezone =>
      string(3) "GMT"
    }
    

    Why this is though, I cannot find in the documentation. If you do:

    echo date('T');
    // CST
    

    ...you get back the timezone abbreviation without surrounding parentheses. But according to the linked DateTime::createFromFormat() docs, ;, :, /, ., ,, -, ( or ) should be interpreted literally.

    Oh, here it gets a little interesting:

    // Works!!
    $d = DateTime::createFromFormat('D, d M Y H:i:s O (T', 'Fri, 21 Feb 2014 14:02:37 +0000 (GMT)');
    //-----------------------------------------------^^^ Open but no close ) 
    var_dump($d);
    class DateTime#6 (3) {
      public $date =>
      string(19) "2014-02-21 14:02:37"
      public $timezone_type =>
      int(2)
      public $timezone =>
      string(3) "GMT"
    }
    
    // Fails!!
    $d = DateTime::createFromFormat('D, d M Y H:i:s O (T)', 'Fri, 21 Feb 2014 14:02:37 +0000 (GMT)');
    // -----------------------------------------------^^^^ open and close ()
    var_dump($d);
    bool(false)
    

    It appears this could be related to the T timezone parsing behavior identified in this answer, wherein the timezone abbreviation string is parsed only up to the final ).