MySQL UNIX_TIMESTAMP acting weird - php

In my database I have a datetime field with the following value 2014-07-21 00:00:00.
When I pull the data I have the line:
SELECT UNIX_TIMESTAMP(date) AS `date` ...
When I then use PHP date to format it for human reading the following happens:
echo date('d/m/Y H:i:s', $row['date']);
// outputs 20/07/2014 23:00:00
I don't understand what's doing this.

It's a timezone problem. 2014-07-21 00:00:00 will convert to very different UNIX timestamps depending on what timezone the database assumes this time to be in. Conversely, PHP will convert the UNIX timestamp to the human-readable version depending on the timezone set with date_timezone_default_set. You'll have to ensure that MySQL's internal timezone setting and PHP's internal timezone setting are identical if you expect the same value to be output.

I replicated the same in my database and I got exactly the same value. I cannot say if you and I are in the same timezone, but one thing is sure - according to the documentation Here
If UNIX_TIMESTAMP() is called with a date argument, it returns the value of the argument as seconds since '1970-01-01 00:00:00' UTC
That explains the disparity.
To solve the problem you can select the date normally and use strtotime in php to convert it to timestamp. As in
SELECT date AS `date` ...
echo date('d/m/Y H:i:s', strtotime($row['date']));
Hope this helps..cheers!

Related

Why can't I use php time() for a timestamp column?

I have a timestamp column in a db table. Saving values with:
UPDATE `table` SET `activated_at` = CURRENT_TIMESTAMP WHERE `id` = 123;
works fine.
But when I use the php function time() to get the timestamp, it doesn't work. It only works using date('Y-m-d H:i:s') for the column value. Question is why?
the column definition is:
`activated_at` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00'
I'm using the php mysql extension (and yes, I know it's deprecated, but I have to maintain some legacy code)
Since time() in php return a unix timestamp and timestamp is a datetime type and it requeires a valid datetime value.If you didnt give a valid datetime value it will be storing like 0000-00-00 00:00:00. If you want to keep your field as datetime type then you must give date('Y-m-d H:i:s') in php
Also check the documention of various date time types in mysql
time() returns a unix timestamp, but the MySQL timestamp column supports specific formats such as YYYY-MM-DD HH:II:SS. You can easily do the conversion using date for PHP or FROM_UNIXTIME in mysql.
Look here
The TIMESTAMP data type is used for values that contain both date and time parts. TIMESTAMP has a range of '1970-01-01 00:00:01' UTC to '2038-01-19 03:14:07' UTC.
MySQL converts TIMESTAMP values from the current time zone to UTC for storage, and back from UTC to the current time zone for retrieval. (This does not occur for other types such as DATETIME.) By default, the current time zone for each connection is the server's time. The time zone can be set on a per-connection basis. As long as the time zone setting remains constant, you get back the same value you store. If you store a TIMESTAMP value, and then change the time zone and retrieve the value, the retrieved value is different from the value you stored. This occurs because the same time zone was not used for conversion in both directions. The current time zone is available as the value of the time_zone system variable. For more information, see Section 10.6, “MySQL Server Time Zone Support”
*nix timestamp and MySQL TIMESTAMP is not the same... that's why you need convert from *nix timestamp to MySQL timestamp over date('Y-m-d H:i:s', $unix_timestamp)
if you want to use time() change the column type to varchar(15)

mysql inserting to datetime not outputing correct time

I want to save to database a given date with this format:
date('Y-m-d H:i:s')
Using datetime datatype, it outputs:
2012-10-29 00:18:14
To check if it gives the correct output, I add to my table a timestamp which returns the current date and time of the insertion/update, it returns:
2012-10-29 07:18:14
I suspect that there is something wrong with my format.
sounds like a timezone issue.
you can use date_default_timezone or the date.timezone ini setting to have PHP use the same timezone as MySQL.
you can see the MySQL timezone with:
select ##session.time_zone;
you definitely want to use this format: date('Y-m-d H:i:s') according to php manual (http://php.net/manual/en/function.date.php) - "H" is used for 24 hour time format, "h" is used for 12 hour format, mysql will use a 24hr clock. MySQL standard format is "Y-m-d H:i:s"
However, you are getting hit with timezone here. I bet you are 7 hrs from UTC. try setting your timezone first:
date_default_timezone_set('UTC'); or whatever timezone you want.
TIMESTAMP is stored in UTC (GMT) http://dev.mysql.com/doc/refman/5.5/en/datetime.html while DATETIME is not, hence your difference.

php timestamp utc

I have a PHP MySQL query that inserts some data into a MySQL database and it includes a timestamp.
Currently the INSERT query uses NOW() for the the timestamp column and it is saved in the database in the following format: 2012-07-24 13:13:02
Unfortunately for me the Server is not in my time zone and it is listed as America/Los_Angeles as shown print date_default_timezone_get();
I was hoping to do the following:
date_default_timezone_set('Europe/London');
$timefordbLondonEU = date('Y-m-d H:i:s', time());
and simply save into the database the $timefordbLondonEU in place of the NOW();
Is this a good way to save such data ?
Many Thanks,
Richard
[ADDED TEXT]
I changed the Type in the MySQL db to DateTime and did the following:
date_default_timezone_set('Europe/London');
$timefordbLondonEU = date('Y-m-d H:i:s', time());
It is working but Im still not getting the overall concept yet.
Assumptions based on your comments:
MySQL = Does not have a datatype UTC you simply use type INT.
Unix_TimeStamp() will save the current time or count? in UTC format such as 1343247227.
As UTC is a count from a common 0 point you can get any timezone from it. Assuming that you don't want a date before the reference 0 point in 1970.
My guess and lead on from what you have said is the best way to do it is save the time as UTC in an INT (1343247227) and then generate any time zones you want from there. Again assuming you don't need to store dates before the reference 0 point in 1970.
Equally why not store as datetime YYYY-MM-DD HH:MM:SS at a known timezone and then convert to UTC or other timezones. It all seems pretty messy =(
As #Petah said in the comments, store your times in UTC and covert them in the application as needed.
Unix timestamps are in UTC so I usually store my times in the database as timestamps. This saves the headache and confusion of first converting to UTC to insert, and then from UTC when selecting.
That is, make your time field an INT type, and use the function UNIX_TIMESTAMP() in MySQL when you insert, or get the timestamp from PHP using the time() function.
When you fetch the timestamp from the DB it will be in UTC, but when you display it in your PHP application using date(), it will display in the server timezone, or whatever you set with date_default_timezone_set.
Therefore the following two queries will work:
INSERT INTO `table` (id, time) VALUES(NULL, UNIX_TIMESTAMP());
// or
$time = time();
$query = "INSERT INTO `table` (id, time) VALUES(NULL, $time);
If you want to select it from the DB as a DATETIME, you can do this:
SELECT *, FROM_UNIXTIME(time) as dt FROM `table` WHERE 1
The resulting dt column will be in the format yyyy-MM-dd hh:mm:ss.
You can format the numeric timestamp in PHP using date()
If the PHP version you have is 64-bit, you aren't limited to the 1970 - 2036 range, PHP will support 64-bit timestamps, just make sure to use a BIGINT column in MySQL in that case.
Hope that helps.

mysql UNIX_TIMESTAMP returns incorrect value

I have the following date in mysql stored in DATETIME field:
2012-04-16 16:21:54
Than I select it like this:
SELECT UNIX_TIMESTAMP(date) ....
but if I print the hour using php date function I get one hour difference:
echo date("H:i:s", $row->date)
would print:
17:21:54
Without the second parameter, the date function returns correct value. Any ideas?
According to mysql manual -
UNIX_TIMESTAMP(), UNIX_TIMESTAMP(date)
If called with no argument, returns a Unix timestamp (seconds since '1970-01-01 00:00:00' UTC) as an unsigned integer. If UNIX_TIMESTAMP() is called with a date argument, it returns the value of the argument as seconds since '1970-01-01 00:00:00' UTC. date may be a DATE string, a DATETIME string, a TIMESTAMP, or a number in the format YYMMDD or YYYYMMDD. The server interprets date as a value in the current time zone and converts it to an internal value in UTC. Clients can set their time zone as described in Section 10.6, “MySQL Server Time Zone Support”.
with adding 'e' you can get the timezone for that timestamp.
It has probably something to do with different timezones. Try using http://www.php.net/manual/en/function.date-timezone-set.php.
If that won't work, explore the rest of the date function:
http://php.net/manual/en/book.datetime.php

MySQL convert DateTime (storing a UTC_TIMESTAMP) to number of seconds 1970

There are many similar questions out there but I believe this one is unique. (Sorry if it isn't)
Our database has datetime field named "date_sampled", of which we store with UTC_TIMESTAMP()
Our goal is to return the number of seconds since 1970. I noticed UNIX_TIMESTAMP() if supplied no argument returns the current UNIX_TIMESTAMP() and if a datetime (i.e. 2011-10-10) is passed, it returns a timestamp in seconds.
However UTC_TIMESTAMP() does not work like this, it Only returns a current UTC Timestamp.
So how can I convert my DateTime field (holding a UTC datetime) into the seconds from 1970 in MySQL? If it can't be done in MySQL, then a PHP solution will work.
Thanks.
There is a TIMESTAMPDIFF function in MySQL, you can use it something like
SELECT TIMESTAMPDIFF(SECOND,'1970-01-01 00:00:00', YourUTCDateFromSomewhere)
More details in the docs - http://dev.mysql.com/doc/refman/5.1/en/date-and-time-functions.html#function_timestampdiff
What were you trying to get UTC_TIMESTAMP to do that UNIX_TIMESTAMP doesn't? Unix timestamps are in UTC by definition.
I'm assuming the problem you're having is that, even though you're storing your datetimes in UTC, UNIX_TIMESTAMP is giving you a timezone-offset result, so you're getting a value several hours off from what you're expecting.
UNIX_TIMESTAMP respects MySQL's time_zone variable, so if all your dates are in UTC, you can just set your session's time_zone variable to UTC, which will cause UNIX_TIMESTAMP to do no timezone conversion when converting a datetime to a timestamp.
SET time_zone = '+00:00'
Interesting problem... I have no clue how to do this with SQL... but the PHP solution would be to use the strtotime() function..
<?php
echo strtotime('2011-10-10');
?>
The above example returns the value 1318219200 which is the number of seconds that have passed since the 1970 epoch

Categories