2009-12-04 9 views
16

Estoy trabajando en una API que necesita cargar todos los archivos .rb en su directorio actual y todos los subdirectorios. Actualmente, estoy ingresando una nueva declaración de requerimiento para cada archivo que agrego, pero me gustaría hacerlo donde solo tengo que colocar el archivo en uno de los subdirectorios y hacer que se agregue automáticamente.¿Es posible solicitar de forma recursiva todos los archivos en un directorio en Ruby?

¿Hay un comando estándar para hacer esto?

+1

Solo una nota: SOLICITAR un conjunto de archivos posiblemente desconocidos es peligroso y también puede provocar errores. Digamos que puse un archivo llamado die.rb con una declaración de salida (lo siento, no hay código real, nunca he usado Ruby), tan pronto como se carga, el programa termina. ¿O qué sucede si el usuario elimina un archivo? Las funciones proporcionadas por ese archivo no se cargarán. Si solo desea ignorar el problema de seguridad, incluidos los archivos y verificar que estén cargados (llamando a algún tipo de función de comprobación), podría funcionar, pero de nuevo, no hay experiencia de Ruby. – HalfBrian

Respuesta

39

En este caso sus Carga todos los archivos en el directorio lib:

Dir["#{File.dirname(__FILE__)}/lib/**/*.rb"].each { |f| load(f) } 
+1

¿por qué usas 'load' y no' require'? – johannes

+0

Puede usar ambos, pero requieren generalmente se pasa un nombre de biblioteca, sin extensión, en lugar de un nombre de archivo. –

+1

pero 'require', no importa si pasa la extensión, por lo que en mi opinión es preferible – johannes

6
require "find" 

Find.find(folder) do |file| 
    next if File.extname(file) != ".rb" 
    puts "loading #{file}" 
    load(file) 
end 

Esto cargará recursivamente cada archivo .rb.

0
def rLoad(dir) 
    Dir.entries(dir).each {|f| 
     next if f=='.' or f=='..' 
     if File.directory?(f) 
      rInclude(f) 
     else 
      load(f) if File.fnmatch('*.rb', f) 
     end 
    } 
end 

Esto debería recursivamente todos los archivos load .RB en el directorio especificado por dir. Por ejemplo, rLoad Dir.pwd funcionaría en el directorio de trabajo actual.

Tenga cuidado al hacer esto, sin embargo. Esto hace una búsqueda en profundidad y si hay definiciones conflictivas en sus scripts de Ruby, pueden resolverse de alguna manera no obvia (alfabéticamente por carpeta/nombre de archivo, creo).

+0

¿Por qué no estás haciendo una coincidencia directa con 'f' en tu llamada de carga? – Geo

+0

Si se refiere a la declaración 'File.fnmatch ('*. Rb', f)', la instrucción devuelve verdadero si el nombre de archivo 'f' coincide con el patrón' * .rb'. Esto asegura que solo estamos 'cargando '' scripts de ruby ​​y no otros archivos que puedan estar en la carpeta. Tenga en cuenta que puede tener que agregar otra condición si también tiene algunos scripts que usan la extensión .rbw. – bta

+0

Sí. Pero podrías haber usado 'load (f) if f = ~/\. Rb /'. Me refería a por qué estás usando fnmatch sobre el soporte regex incorporado. – Geo

0

Deberías echarle un vistazo a este gem. Es bastante pequeño para que pueda volver a utilizar el código en lugar de instalar toda la gema.

+0

El enlace está roto. – juan2raid

+0

http://github.com/mlightner/require_directory esto debería funcionar. – Waseem

2

como Miguel Fonseca dijo, pero en ruby> = 2 que puede hacer:

Dir[File.expand_path "lib/**/*.rb"].each{|f| require_relative(f)} 
2

utilizo la gema require_all todo el tiempo, y se hace el trabajo con el siguiente patrón en su requiere:

require 'require_all' 
require_all './lib/exceptions/' 
Cuestiones relacionadas