-
-
Notifications
You must be signed in to change notification settings - Fork 147
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
DateTime: createFromFormat() returns Nette\Utils\DateTime instance #6
Conversation
if (func_num_args() === 3 && !$timezone instanceof \DateTimeZone) { | ||
throw new Nette\InvalidArgumentException('Nette\Utils\DateTime::createFromFormat() expects parameter 3 to be DateTimeZone, ' . gettype($timezone) . ' given'); | ||
} | ||
$datetime = call_user_func_array('parent::createFromFormat', func_get_args()); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this cannot be done without call_user_func_array
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It can, see the note in the PR description, I will change it to if
then, I suppose.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I see, it doesn't work when you pass NULL in variable? It has to be called without the third parameter?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Exactly. The 3rd parameter has to be a DateTimeZone
instance or it must not be passed at all. (I hate PHP so much in these regards)
The other variant has a condition if ($timezone !== NULL)
then call parent method with 3 params, otherwise call with it with 2 (both filling $datetime
variable, the last line remains the same).
Which is better?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I guess this one is fine. But it didn't work in some versions of PHP (I guess the old ones). But travis passes, so fuck it :)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Very well.
If you mean the "parent::foo"
, I searched for similar uses in Nette, and it is used e.g. in Nette\Database
, so I figured it shouldn't be a problem.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just use 3v4l.org if you are not sure which version does what.
👍 I hit this problem too. I personally prefer the 3rd argument can be NULL so: $datetime = $zone === NULL
? parent::createFromFormat($format, $time)
: parent::createFromFormat($format, $time, $zone);
return static::from($datetime); What others? And I think there can be annotations there it has meening. |
@milo Me too. It is pretty annoying how PHP handles this, but I didn't want to change the behaviour of the parent method. So, they act the same just the new one returns the correct instance. What annotations do you mean? |
Just a thought: you could add the timezone created using |
@fprochazka Or even better: allow passing string as timezone and automatically create the DateTimeZone object. |
@fprochazka I thought of that too. @xificurk It changes the parent's default behaviour a lot but I like it. |
@@ -86,4 +86,14 @@ public function getTimestamp() | |||
return is_float($tmp = $ts * 1) ? $ts : $tmp; | |||
} | |||
|
|||
|
|||
public static function createFromFormat($format, $time, $timezone = NULL) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
3rd parameter should be typehinted as DateTimeZone, shouldn't it?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It would be nice, but I cannot change the signature - it has to be compatible with the parent method.
What about this? I find it pretty good now, including the phpdocs. |
|
||
/** | ||
* Returns new DateTime object formatted according to the specified format. | ||
* @param string The format of the passed in $time parameter should be in |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The format of the passed in $time parameter should be in
What would you expect from these calls? createFromFormat('Y-m-d H:i:s', '2014-04-11 12:00:00', 'Pacific/Fiji')
createFromFormat('Y-m-d H:i:sP', '2014-04-11 12:00:00+02:00', 'Pacific/Fiji')
createFromFormat('Y-m-d H:i:sP', '2014-04-11 12:00:00+02:00')
createFromFormat('U', '1397240808')
createFromFormat('U', '1397240808', 'Europe/Prague') |
I think it should do the same as what the docs say about it: |
@redhead Good point |
Is it good to go? (as it is a school assignment I would like it to be merged by the end of the semester.. :-/ if possible ) |
I am not sure that changing method signature (3rd parameter) is good idea. In fact, I am suprised that PHP allowes this. |
There is no type hint, so there is no change in the signature. It is just possible to pass DateTimeZone as well as a string (which is then made into a DateTimeZone instance). Would you like it to be strictly compatible with the parent method (in behaviour)? |
According to documentation of DateTime, 3rd argument has type hint, so it is change. Or isn't? |
@dg It is somehow wrong PHP implementation/documentation. bug 60302, bug 55407 When you add in descendant public static function createFromFormat($format, $time, \DateTimeZone $tz = NULL)
PHP Strict Standards: Declaration of Milo\Dt::createFromFormat() should be compatible
with DateTime::createFromFormat($format, $time, $object = NULL) And when you call \DateTime::createFromFormat('Y-m-d', '2014-04-27', NULL);
PHP Warning: DateTime::createFromFormat() expects parameter 3 to be DateTimeZone, null given Imho It is buggy as much it can be. If we extends |
Yes, it's quite broken. Adding parameter |
So far I feel like these problems can be solved using proxy pattern. (Mask returned objects with proxy and include per PHP version logic that preserves expected behaviour of createformat.) @milo Nette\Datetime is already not future compatible, definitely not binary compatible and breaking single responsibility rule (it also serves as and unix timestamp enum). This is just mine opinion, no need to discuss it. That bridge will be crossed when PHP gets there (5.7+). I just hope that any solution won't become like Nette\Callback. (replacing native functionality, and being removed in next version) |
$timezone = new \DateTimeZone($timezone); | ||
} | ||
|
||
if (!$timezone instanceof \DateTimeZone) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here should be elseif
Updated according to David's notes. |
Can you squash it to simple commit? |
Done. |
DateTime: createFromFormat() returns Nette\Utils\DateTime instance
Static factory method
createFromFormat()
now returnsNette\Utils\DateTime
instance instead of PHP's\DateTime
.This fixes somewhat unexpected behaviour when calling factory method on a
Nette\Utils\DateTime
class and receiving an instance of different class.Closes nette/nette#1258.
Note: I used
call_user_func_array()
because the third parameter is optional and cannot beNULL
for the parent method. I didn't want to use anif
condition just for this (but if it is found ugly I will update it).