11
votes

I have a server in GMT but I want to update those fields ( *created_at* and *updated_at* ) to save timestamps in PST.

I've already did some tests trying to accomplish this but none of them were correct.

  • I update the config/application.php to 'timezone' => 'America/Los_Angeles'
  • Also in the server I've change the date.timezone in php.ini to 'America/Los_Angeles'

But any of this updates apply timezone update to the Laravel Eloquent timestamps. This fields created_at and updated_at are handle by Eloquent.

I've also update the Ubuntu server timezone using sudo dpkg-reconfigure tzdata but this update didn't work at all.

Edit: I need to have the Laravel Eloquent timestamps working on PST timezone for futures inserts to the DB.

Any help will be useful. Thanks.

4
to confirm - you want to update the created_at and updated_at columns which are already inside your mysql database?ılǝ
No, I want to have the fields created_at and updated_at aligned to PST for future inserts to the DB. I mean on PHP Laravel side.larc000
In this case your question is not regarding programming and I'm afraid the question is outside the scope of the community. It seems serverfault.com is a better place to search for help.ılǝ
Sorry If I didn't explain myself well, but yes the issue is related to programming, is related to PHP Laravel framework. I need to know if it's possible to modify the timezone used by Eloquent at the moment to save these timestamps created_at and updated_at when its saved to the DB.larc000
I see now... Upvoting, hopefully others will see it. Meanwhile - have a look at this: craigcartmell.com/article/show/2/…ılǝ

4 Answers

22
votes

I know this question is a bit dated, but I stumbled upon it when trying to come up with the same solution, and wanted to share how I went about solving it.

My advice would be not to change the timezone that the messages are stored in. Store them in the database as UTC. Keeping your storage set to a constant frame of reference and then converting it to whatever timezone you need it displayed in will save you loads of headache over the long run.

As an example of one of those headaches, imagine two people trying to coordinate a meeting time in different timezones where one observes DST and one doesn't and you need to display the time in each user's local time. How hard would it be to convert your stored PDT time to say, the America/Cayman (which doesn't observe DST)? And how would you take in account when times are stored in PST vs PDT? How would you know? (Hint: without probably hundreds of lines of extra code just to answer that one question, you won't).

To get the time out in the correct timezone, simply add a mutator function on the model itself:

use Carbon\Carbon;

class MyModel extends Eloquent
{
    public function getCreatedAtAttribute($value)
    {
        return Carbon::createFromTimestamp(strtotime($value))
            ->timezone('America/Los_Angeles')
            ->toDateTimeString()
        ;
    }
}

Now, whenever you do $myModel->created_at it will magically be converted into the correct timezone, but you still keep UTC in your database which definitely has its perks over other timezones for persistent storage.

Want to let users set their own timezones? Change the function to this:

public function getCreatedAtAttribute($value)
{
    $user = Auth::user();
    // If no user is logged in, we'll just default to the 
    // application's timezone
    $timezone = $user ? $user->timezone : Config::get('app.timezone');

    return Carbon::createFromTimestamp(strtotime($value))
        ->timezone($timezone)
        // Leave this part off if you want to keep the property as 
        // a Carbon object rather than always just returning a string
        ->toDateTimeString()
    ;
}

And all of the complexity of changing timezones, taking daylight savings into account or not is abstracted away from you and you can forget that it even has to happen.

For more information about Laravel mutators / accessors, checkout the documentation.

3
votes

I am not absolutely sure I understand if you want to change the setting of the server for future entries to the database, or if you want to update the current values in your database.

If it is the latter, changing your server settings will not effect the current records in the database. If you want to change the values of the existing fields, you can do that with an MySQL command like:

 update `table` set created_at = (SELECT created_at) + INTERVAL 2 HOUR;

Where table is the name of the database table and 2 is the offset in hours.

2
votes

it's simple,just modify function boot() in AppServiceProvider.php

public function boot()
{
    //set local timezone
    date_default_timezone_set('Asia/Shanghai');
}
0
votes

For Lumen it works with this in .env file:

DB_TIMEZONE="+03:00"