How to Change Default Timezone For Active Record in Rails

How to change default timezone for Active Record in Rails?

adding following to application.rb works

 config.time_zone = 'Eastern Time (US & Canada)'
config.active_record.default_timezone = :local # Or :utc

Rails set config.active_record.default_timezone to value other than :utc or :local

Looking at the PostgreSQLAdapter source on github, I saw that a variables hash is checked for the presence of a "timezone" key.

      variables = @config.fetch(:variables, {}).stringify_keys

# If using Active Record's time zone support configure the connection to return
# TIMESTAMP WITH ZONE types in UTC.
unless variables["timezone"]
if ActiveRecord::Base.default_timezone == :utc
variables["timezone"] = "UTC"
elsif @local_tz
variables["timezone"] = @local_tz
end
end

The PostgreSQLAdapter docs show that :variables is an option in config/database.yml, so I just added variables: {timezone: 'US/Pacific'} to database.yml.

# database.yml
default: &default
adapter: postgresql
encoding: unicode
pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>
variables: {timezone: 'US/Pacific'}

Kind of weird that you have to set it here instead of in config/, but it works.

Change default_timezone of active record

This is dangerous, but here is what I'd do in the migration:

class MigrateDateTimesFromUTCToLocal < ActiveRecord::Migration

def self.up
# Eager load the application, in order to find all the models
# Check your application.rb's load_paths is minimal and doesn't do anything adverse
Rails.application.eager_load!

# Now all the models are loaded. Let's loop through them
# But first, Rails can have multiple models inheriting the same table
# Let's get the unique tables
uniq_models = ActiveRecord::Base.models.uniq_by{ |model| model.table_name }

begin
# Now let's loop
uniq_models.each do |model|
# Since we may be in the middle of many migrations,
# Let's refresh the latest schema for that model
model.reset_column_information

# Filter only the date/time columns
datetime_columns = model.columns.select{ |column| [ :datetime, :date, :time].include? column.type }

# Process them
# Remember *not* to loop through model.all.each, or something like that
# Use plain SQL, since the migrations for many columns in that model may not have run yet
datetime_columns.each do |column|
execute <<-SQL
UPDATE #{model.table_name} SET #{column.name} = /* DB-specific date/time conversion */
SQL
end

rescue
# Probably time to think about your rescue strategy
# If you have tested the code properly in Test/Staging environments
# Then it should run fine in Production
# So if an exception happens, better re-throw it and handle it manually
end

end
end
end

Rails 5 API: Globally Set config.time_zone to UTC

you should use Time.zone.now instead of Time.now or Time.now.utc

Good explanation here

https://rails-bestpractices.com/posts/2014/10/22/use-time-zone-now-instead-of-time-now/

http://danilenko.org/2012/7/6/rails_timezones/

MySQL - setting default timezone for a Rails application

From: http://guides.rubyonrails.org/configuring.html#configuring-active-record

config.time_zone sets the default time zone for the application and
enables time zone awareness for Active Record.

config.active_record.default_timezone determines whether to use
Time.local (if set to :local) or Time.utc (if set to :utc) when pulling
dates and times from the database. The default is :local.

So based on this, if you want to override your default timezone to Eastern time, you'd want to do:

config.time_zone = 'Eastern Time (US & Canada)'
config.active_record.default_timezone = :local

Let me know if this helps!

Rails. Set default timezone when current_user loaded

I think the safest approach here would be to use the around_action like such, make sure to specify which action you want this to happen on:

class SomeController < ApplicationController
around_action :set_time_zone, only: :show

private

def set_time_zone
if current_user
Time.zone = current_user.settings(:main).time_zone
end
yield
end
end


Related Topics



Leave a reply



Submit