# frozen_string_literal: true
module ActiveAdminContentsRollback
  def files
    @files ||= {}
  end

  # Records the contents of a file the first time we are
  # about to change it
  def record(filename)
    contents = File.read(filename) rescue nil
    files[filename] = contents unless files.has_key? filename
  end

  # Rolls the recorded files back to their original states
  def rollback!
    files.each { |file, contents| rollback_file(file, contents) }
    @files = {}
  end

  # If the file originally had content, override the stuff on disk.
  # Else, remove the file and its parent folder structure until Rails.root OR other files exist.
  def rollback_file(file, contents)
    if contents.present?
      File.open(file, "w") { |f| f << contents }
    else
      File.delete(file)
      begin
        dir = File.dirname(file)
        until dir == Rails.root
          Dir.rmdir(dir) # delete current folder
          dir = dir.split("/")[0..-2].join("/") # select parent folder
        end
      rescue Errno::ENOTEMPTY # Directory not empty
      end
    end
  end
end

World(ActiveAdminContentsRollback)

After "@changes-filesystem or @requires-reloading" do
  rollback!
end

Given(/^"([^"]*)" contains:$/) do |filename, contents|
  path = Rails.root + filename
  FileUtils.mkdir_p File.dirname path
  record path

  File.open(path, "w+") { |f| f << contents }
end

Given(/^I add "([^"]*)" to the "([^"]*)" model$/) do |code, model_name|
  path = Rails.root.join "app", "models", "#{model_name}.rb"
  record path

  str = File.read(path).gsub(/^(class .+)$/, "\\1\n  #{code}\n")
  File.open(path, "w+") { |f| f << str }
end
