Advertisement
c00lways

Rails export raw seed data

Jan 31st, 2016
143
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Ruby 4.02 KB | None | 0 0
  1. # calling from task
  2. rails g task export all
  3. # example call from task
  4. # lib/tasks/export.rb
  5. namespace :export do
  6.   desc "export seeds data"
  7.   task all: :environment do
  8.     Mstudio::DataTools.export_sql({exclude_tables: ['visits','events', 'versions', 'ahoy_events', 'sessions']})
  9.   end
  10. end
  11.  
  12. # exporting it
  13. RAILS_ENV=production rake export:all
  14. # next, adding raw sql to seed file:
  15.  
  16. # db/seeds.rb
  17. import_sql(Rails.root.join('db').join('seeds').join('all.sql'))
  18. def import_sql(path)
  19.   connection = ActiveRecord::Base.connection()
  20.  
  21.   sql = File.read(path)
  22.   if Rails.env.development?
  23.     statements = sql.split(/;\r$/)
  24.   else
  25.     statements = sql.split(/;$/)
  26.   end
  27.   statements.pop
  28.  
  29.   ActiveRecord::Base.transaction do
  30.     statements.each do |statement|
  31.       connection.execute(statement)
  32.     end
  33.   end
  34. end
  35.  
  36. # next, importing it to staging or development
  37. RAILS_ENV=staging rake db:reset
  38.  
  39. # lib/extras/mstudio/data_tools.rb
  40. module Mstudio
  41.   class DataTools
  42.    
  43.     def self.export_sql(options = {tables: nil, exclude_tables: nil, output_file: nil })
  44.       path = options[:output_file] || Rails.root.join('db').join('seeds').join('all.sql')
  45.       excluded_tables = options[:exclude_tables]
  46.       tables = []
  47.       if options[:tables].nil? || options[:tables].to_s == "*"
  48.         ActiveRecord::Base.connection.tables.each do |table|
  49.           tables << table if table != 'schema_migrations'
  50.         end
  51.       end
  52.      
  53.       File.open(path, 'w:UTF-8') { |file|
  54.         tables.each do |table|
  55.           if excluded_tables.nil? || !excluded_tables.include?(table)
  56.             model_class = model_class(table)
  57.             # puts "model: #{model_class.inspect}"
  58.             export_table(model_class.order('id asc'), table, file)
  59.             file.write("\n\n")
  60.           end
  61.         end #table
  62.       } # file write
  63.      
  64.     end
  65.    
  66.     def self.export_table(records, table, file)
  67.       records.each do |row|
  68.         export_rows(row, file)
  69.       end
  70.     end
  71.    
  72.     def self.export_rows(model, file)
  73.       data = model.attributes
  74.       fields = []
  75.       values = []
  76.       data.each do |field, value|
  77.         # skip nil for integer issues
  78.         unless value.nil?
  79.           fields << "#{column_delimiter}#{field}#{column_delimiter}"
  80.           if value.blank? && field.end_with?('_at')
  81.             values << "NULL"
  82.           else
  83.             values << "'#{escape_db_value(value)}'"
  84.           end
  85.         end
  86.       end
  87.      
  88.       if fields.size > 0
  89.         sql = "INSERT INTO #{column_delimiter}#{model.class.table_name}#{column_delimiter} (#{fields.join(',')}) VALUES "+
  90.           "(#{values.join(',')});"
  91.         # block_row.call(model, model.class.table_name, file) unless block_row.nil?
  92.         file.write(sql+"\n")
  93.       end
  94.      
  95.       sql
  96.     end
  97.    
  98.     def self.escape_db_value(value)
  99.       return nil if value.blank?
  100.       if value.is_a?(Date) || value.is_a?(Time)
  101.         return value.iso8601
  102.       end
  103.       return value unless value.is_a?(String)
  104.       clean = value.gsub('\'', '\'\'')
  105.     end
  106.    
  107.     def self.column_delimiter
  108.       case ActiveRecord::Base.connection.adapter_name.downcase.to_sym
  109.       when :mysql
  110.         "`"
  111.       when :sqlite
  112.         "`"
  113.       when :postgresql
  114.         '"'
  115.       else
  116.         raise NotImplementedError, "Unknown adapter type '#{adapter_type}'"
  117.       end
  118.     end
  119.    
  120.     def self.model_class(table)
  121.       # external gems models
  122.       # case table
  123.       # when 'versions'
  124.       #   return ::Version
  125.       # end
  126.      
  127.       Dir[Rails.root.join("app", "models", "**", "*.rb")].each do |path|
  128.         unless path.include?('concerns')
  129.           require(path)
  130.         end
  131.         # (&method(:require))
  132.       end
  133.      
  134.       tables = Hash[ActiveRecord::Base.send(:descendants).collect{|c| [c.table_name, c]}]
  135.       raise Exception, "Table missing: #{table}" unless tables.include?(table)
  136.       tables[table]
  137.     end
  138.    
  139.     def self.model_name(table)
  140.       model = model_class(table)
  141.       model.class_name
  142.     end
  143.    
  144.   end
  145.  
  146. end
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement