从Controller / Helper,Ruby on Rails重置DB

时间:2016-09-06 13:36:04

标签: ruby-on-rails ruby postgresql ruby-on-rails-4

我已经创建了我的程序演示。该演示用于向客户展示该程序。在每次演示之前,我想重置数据库,并插入某些数据,我必须做的动作是:

rake db:drop
rake db:setup
rake db:seed:demo

但是他们并不总是我提供它而其他人不使用控制台,因此我想在设置页面中设置通过按钮重置的功能。

我试过这样的方式:

module SettingsHelper
require 'rake'
  def reset
        Rake::Task[db:drop].invoke
        Rake::Task[db:setup].invoke
        Rake::Task[db:seeds:demo].invoke
  end
end

我提出以下表格:

  <%=button_to "Reset", reset, class:"btn red" %>

但我无法使用活动服务器删除数据库......我该怎么办?

2 个答案:

答案 0 :(得分:1)

在有活动连接时,无法删除数据库。相反,你可以做的是发出一个TRUNCATE命令,它删除表中的所有行并重置ID列。

如果您希望对截断的哪些表进行更精细的控制,可以向模型添加类方法:

class User < ActiveRecord::Base
  self.truncate!
    self.connection.execute(
      "TRUNCATE TABLE #{ self.table_name };"
    )
    self.connection.reset_pk_sequence!(self.table_name)
  end
end 

但是让我们将它干燥到一个模块中,这样我们就不必在应该具有这种行为的所有模型中重复它:

# app/models/concerns/resetable.rb
module Resetable
  extend ActiveSupport::Concern
  class_methods do
    def truncate!
      self.connection.execute(
        "TRUNCATE TABLE #{ self.table_name };"
      )
      self.connection.reset_pk_sequence!(self.table_name)
    end
  end
end

# app/models/user.rb
class User < ActiveRecord::Base
  include Resetable
  # ...
end 

 # app/models/book.rb
class Book < ActiveRecord::Base
  include Resetable
  # ...
end 
# ...

然后,您可以通过以下方式重置每个模型的数据:

def reset_db
  [User, Book, Thing].each { |model| model.truncate! }
  Rails.application.load_seed
end

如果您只想核对所有表格,您可以这样做:

ActiveRecord::Base.connection.tables.each do |t|
  conn = ActiveRecord::Base.connection
  conn.execute("TRUNCATE TABLE #{t} CASCADE;")
  conn.reset_pk_sequence!(t)
end

答案 1 :(得分:0)

我从以下SO答案中摘取了一些代码

你可以在控制器中添加这样的东西

def reset_db
  conn = ActiveRecord::Base.connection
  tables = ActiveRecord::Base.connection.tables
  tables.each { |t| conn.execute("TRUNCATE #{t}") }

  Rails.application.load_seed
end