Приложение Rails и sqlite (dev) против postgresql (prod)

Я изучаю RoR, и моя база данных разработки используется по умолчанию, sqlite, и я развертываю свое приложение в Heroku, которое использует posgresql. Я понимаю, что для избежания таких проблем, я должен разрабатывать и с postgresql, и в будущем я собираюсь это сделать. Однако у меня есть проблема, которая появляется в производстве, но не в разработке.

Проблема: у меня есть модели User и Account. У User может быть много Accounts.

Я сделал миграцию, чтобы при создании Account для его поля active по умолчанию было установлено значение true.

class UpdateDefaultAccountActiveValue < ActiveRecord::Migration
  def change
    change_column_default(:accounts, :active, true)
  end
end

Кажется, это работает в dev.

В /views/accounts/index.html.erb следующий код выводит true или false в зависимости от того, активна учетная запись или нет.

<% @accounts.each do |account| %>
    <tr>
      <% if !(account.credit) %>
        <td><%= link_to account.name, history_url(id: account.id) %></td>
      <% else %>
        <td><%= link_to account.name + ' (Credit)', history_url(id: account.id) %></td>
      <% end %>
      <td><%= account.active %></td>
      <td><%= link_to 'Edit', edit_account_path(account) %></td>
    </tr>
<% end %>

Однако в производственной среде /views/accounts/index.html.erb не выводит true или false в зависимости от того, активна учетная запись или нет.

Почему это и как я могу это решить?

бумажный журнал:

2016-05-25T21:34:06.348465+00:00 app[web.1]: Started GET "/accounts" for 176.248.123.34 at 2016-05-25 21:34:06 +0000

2016-05-25T21:34:06.355649+00:00 app[web.1]: Processing by AccountsController#index as HTML

2016-05-25T21:34:06.447420+00:00 app[web.1]: Completed 200 OK in 94ms (Views: 64.5ms | ActiveRecord: 18.2ms)

2016-05-25T21:34:06.452111+00:00 heroku[router]: at=info method=GET path="/accounts" host=???.herokuapp.com request_id=f33ab960-5c1b-4883-a28c-8c2b40388bad fwd="176.248.123.34" dyno=web.1 connect=0ms service=107ms status=200 bytes=4073

person Bhav    schedule 25.05.2016    source источник
comment
Не могли бы вы показать логи (установите аддон papertrail от heroku, если его еще нет)? Я предполагаю, что значение в столбцах равно нулю, поэтому используйте $heroku run rails console в терминале, найдите экземпляр учетной записи и проверьте атрибут. Если ноль, найдите все экземпляры класса и установите его в значение true. Затем добавьте ограничение null: false в столбец базы данных с миграцией. Дополнительно: измените порядок двух опций и используйте <% if account.credit %>. И вам следует как можно скорее изменить базу данных разработки на pg.   -  person Sean Magyar    schedule 26.05.2016
comment
@SzilardMagyar Я установил papertrail, и он прикреплен к моему приложению. Как просмотреть журналы?   -  person Bhav    schedule 26.05.2016
comment
2 способа: 1. из терминала: $heroku logs --tail 2. из papertrail: вы просто нажимаете на papertrail из панели управления heroku   -  person Sean Magyar    schedule 26.05.2016
comment
@SzilardMagyar Я приложил журнал к ОП.   -  person Bhav    schedule 26.05.2016
comment
В журналах все нормально, вы получаете код состояния 200. Вы проверили значения атрибута логического поля?   -  person Sean Magyar    schedule 26.05.2016
comment
@SzilardMagyar Да, были нулевые значения, которые я теперь изменил на true.   -  person Bhav    schedule 26.05.2016


Ответы (2)


Чтобы установить свойство модели при создании записи, вы должны изменить его внутри модели, если вы запустите миграцию, это поможет только с существующими записями.

Вам нужно добавить три строки кода в вашу модель, чтобы она работала для новых созданных учетных записей:

before_save do
 self.active = true
end
person They_Call_Me_Joe    schedule 25.05.2016
comment
Извините за дождь на вашем параде, но почти все в этом ответе неверно. Если вы установите значение по умолчанию в схеме БД, ActiveRecord установит его для новых экземпляров модели. Когда вы добавляете или изменяете базу данных по умолчанию, это влияет только на новые строки/записи. Этот обратный вызов будет изменяться self.active = true каждый раз, когда вы обновляете учетную запись! - person max; 26.05.2016

Это может не решить именно ту проблему, с которой вы столкнулись, но есть гораздо лучший способ добавить в модель отдельные состояния, чем логические флаги.

ActiveRecord::Enum позволяет создать атрибут перечисления, в котором значения сопоставляются целым числам в база данных.

class Account
  enum status: [:active, :closed, :supended] # basically whatever you want
end

Acount.active     # => Acount.where(status: :active)
acount.active!    # => Acount.update!(status: :active)
acount.active?    # => true
acount.closed?    # => false
acount.suspended? # => false
acount.status     # => "active"

Конечно, вам нужно добавить целочисленный столбец в базу данных:

rails g migration add_status_to_accounts status:integer:index

Пока не переносите его! Мы также хотим добавить значение по умолчанию:

class AddStatusToAccounts < ActiveRecord::Migration
  def change
    add_column :accounts, :status, :integer, default: 0, null: false
    add_index :accounts, :status
  end
end
person max    schedule 26.05.2016