require 'ostruct' module FactoryDataPreloader class PreloaderAlreadyDefinedError < StandardError; end class PreloadedRecordNotFound < StandardError; end class DefinedPreloaderNotRunError < StandardError; end class ErrorWhilePreloadingRecord < StandardError; end module DataMethods end class FactoryData @@single_test_cache = {} extend DataMethods class << self # An Array of strings specifying locations that should be searched for # factory_data definitions. By default, factory_data_preloader will attempt to require # "factory_data," "test/factory_data," and "spec/factory_data." Only the first # existing file will be loaded. attr_accessor :definition_file_paths def preload(model_type, options = {}, &proc) if existing_preloader = AllPreloaders.instance.from_symbol(model_type, false) existing_preloader.remove! end FactoryDataPreloader::Preloader.new(model_type, options[:model_class], proc, options[:depends_on]) DataMethods.class_eval do define_method model_type do |key| FactoryData.send(:get_record, model_type, key) end end end def delete_preload_data! # Delete them in the reverse order of the dependencies, to handle foreign keys FactoryDataPreloader.requested_preloaders.dependency_order.reverse.each do |preloader| preloader.model_class.delete_all end end def preload_data! FactoryDataPreloader.requested_preloaders.dependency_order.each do |preloader| preloader.preload! end end def reset_cache! @@single_test_cache = {} end def find_definitions definition_file_paths.each do |path| require("#{path}.rb") if File.exists?("#{path}.rb") if File.directory? path Dir[File.join(path, '*.rb')].each do |file| require file end end end end private def get_record(type, key) preloader = AllPreloaders.instance.from_symbol(type) @@single_test_cache[type] ||= {} @@single_test_cache[type][key] ||= preloader.get_record(key) end end self.definition_file_paths = %w(factory_data test/factory_data spec/factory_data) end end # alias this class so that apps that use it don't have to use the fully qualified name. FactoryData = FactoryDataPreloader::FactoryData