导出rails数据库数据的最佳方法

时间:2017-10-22 17:04:17

标签: ruby-on-rails ruby-on-rails-5

RAILS 5.1

我有一个使用PostgreSQL作为数据库的RAILS应用程序。我想从RAILS的角度导出/转储RAILS数据库数据。所以我从数据库中独立出来。稍后我想使用此导出/转储文件将数据加载/导入/播种回数据库。

我尝试了以下GEM:

  • seed_dump
    它有效,但它无法处理HABTM模型关系。

  • yaml_db , 它有效,但是yaml格式不是 rails db:seed

  • 所理解的格式

2 个答案:

答案 0 :(得分:2)

这是导出到JSON的实际示例。我使用rake任务来做这种事情。在这个例子中,我正在转储用户表。

namespace :dataexport do
  desc 'export sers who have logged in since 2017-06-30'
  task :recent_users => :environment do
    puts "Export users who have logged in since 2017-06-30"

    # get a file ready, the 'data' directory has already been added in Rails.root
    filepath = File.join(Rails.root, 'data', 'recent_users.json')
    puts "- exporting users into #{filepath}"

    # the key here is to use 'as_json', otherwise you get an ActiveRecord_Relation object, which extends
    # array, and works like in an array, but not for exporting
    users = User.where('last_login > ?', '2017-06-30').as_json

    # The pretty is nice so I can diff exports easily, if that's not important, JSON(users) will do
    File.open(filepath, 'w') do |f|
      f.write(JSON.pretty_generate(users))
    end

    puts "- dumped #{users.size} users"
  end
end

然后导入

namespace :dataimport do
  desc 'import users from recent users dump'
  task :recent_users => :environment do
    puts "Importing current users"

    filepath = File.join(Rails.root, 'data', 'recent_users.json')
    abort "Input file not found: #{filepath}" unless File.exist?(filepath)

    current_users = JSON.parse(File.read(filepath))

    current_users.each do |cu|
      User.create(cu)
    end

    puts "- imported #{current_users.size} users"
  end
end

有时作为导入过程的一部分,我想要一个干净的表格导入,在这种情况下我会开始使用:

ActiveRecord::Base.connection.execute("TRUNCATE users")

这不是处理Really Big表格的最佳方式,大于,50,000行,和/或有大量文本字段。在这种情况下,db本机转储/导入工具会更合适。

为了完整起见,这是一个HABTM示例。还有一个链接表,但它没有模型,因此使用它的唯一方法是原始SQL。让我们假设我们的用户有很多角色,反之亦然(用户M:M角色),例如:

class User < ApplicationRecord
  has_and_belongs_to_many :roles
end

class Role < ApplicationRecord
  has_and_belongs_to_many :users
end

必然会有一个名为users_roles的联接表,它有两列,user_idrole_idSee the Rails Guide on HABTM

要导出,我们必须直接执行SQL:

users_roles = ActiveRecord::Base.connection.execute("SELECT * from users_roles").as_json
# and write the file as before

并执行SQL导入

# read the file, same as before
user_roles.each do |ur|
  ActiveRecord::Base.connection.execute("insert into users_roles (user_id, role_id) values ('#{ur[0]}', '#{ur[1]}')")
end

See this answer for more on inserting with raw SQL

答案 1 :(得分:1)

我同意人们说使用内置的数据库工具来做到这一点。或者弄清楚是否有方法告诉数据库导出为CSV,然后以这种方式导入。

然而,如果您真的想要一种与数据库无关的方式,可以采用另一种方式:使用您自己的API。

我的意思是,2017年你的Rails应用程序不仅应该输出HTML,还应该输出JSON。也许您想在将来编写SPA类型的应用程序或移动应用程序。除了HTML版本之外,确保对象的Javascript表示是一个好主意。

因此,如果您的应用中有/ projects,请编写一个请求/projects为JSON的脚本。将每个对象保存为自己的文件,然后在远程系统中将所有内容发布回来。

如果JSON表示中没有任何内容(即您没有列出项目中的所有用户),请确保同时点击这些端点并将所有内容保存到单独的JSON文件中。

然后编写一个播放器脚本,将所有这些文件发送到您的目标服务。

这是一种方法。还有其他方法是在ActiveRecord中用Ruby完全编写它 - 这可能对某些用户数据导出功能很有用,所以这也可能是一种很棒的方式,但在我看来,我们可以构建这是一个Javascript前端或移动应用程序?&#34;通常在以前被询问,&#34;用户可以获取他们的数据&#34; ;)