web-dev-qa-db-fra.com

One-liner pour lister récursivement les répertoires en Ruby?

Quelle est la manière la plus rapide, la plus optimisée et la plus simple d'obtenir un tableau des répertoires (à l'exception des fichiers) dans Ruby?

Que diriez-vous d'inclure des fichiers?

92
Lance Pollard
Dir.glob("**/*/") # for directories
Dir.glob("**/*") # for all files

Au lieu de Dir.glob(foo), vous pouvez également écrire Dir[foo] (Cependant Dir.glob Peut également prendre un bloc, auquel cas il donnera chaque chemin au lieu de créer un tableau).

Ruby Glob Docs

166
sepp2k

Je crois qu'aucune des solutions ici ne traite des répertoires cachés (par exemple, '.test'):

require 'find'
Find.find('.') { |e| puts e if File.directory?(e) }
53
FelipeC

Pour la liste des répertoires, essayez

Dir['**/']

La liste des fichiers est plus difficile, car dans le répertoire Unix est également un fichier, vous devez donc tester le type ou supprimer les entrées de la liste renvoyée qui est le parent d'autres entrées.

Dir['**/*'].reject {|fn| File.directory?(fn) }

Et pour la liste de tous les fichiers et répertoires simplement

Dir['**/*']
28
MBO

Fast one liner

Uniquement les répertoires

`find -type d`.split("\n")

Répertoires et fichiers normaux

`find -type d -or -type f`.split("\n")`

Pure Beautiful Ruby

require "pathname"

def rec_path(path, file= false)
  puts path
  path.children.collect do |child|
    if file and child.file?
      child
    elsif child.directory?
      rec_path(child, file) + [child]
    end
  end.select { |x| x }.flatten(1)
end

# only directories
rec_path(Pathname.new(dir), false)
# directories and normal files
rec_path(Pathname.new(dir), true)
7
johannes

Comme indiqué dans d'autres réponses ici, vous pouvez utiliser Dir.glob. Gardez à l'esprit que les dossiers peuvent contenir beaucoup de caractères étranges et que les arguments glob sont des modèles, donc certains caractères ont des significations spéciales. En tant que tel, il n'est pas sûr de faire quelque chose comme ceci:

Dir.glob("#{folder}/**/*")

Faites plutôt:

Dir.chdir(folder) { Dir.glob("**/*").map {|path| File.expand_path(path) } }
6
troelskn

En PHP ou dans d'autres langages pour obtenir le contenu d'un répertoire et de tous ses sous-répertoires, vous devez écrire quelques lignes de code, mais en Ruby il faut 2 lignes:

require 'find'
Find.find('./') do |f| p f end

cela affichera le contenu du répertoire courant et de tous ses sous-répertoires.

Ou plus court, vous pouvez utiliser le ’**’ notation:

p Dir['**/*.*']

Combien de lignes écrirez-vous en PHP ou en Java pour obtenir le même résultat?

2
Ramesh

Voici un exemple qui combine la découverte dynamique d'un répertoire de projet Rails avec Dir.glob:

dir = Dir.glob(Rails.root.join('app', 'assets', 'stylesheets', '*'))
0
shacker

Bien que ce ne soit pas une solution sur une seule ligne, je pense que c'est la meilleure façon de le faire en utilisant les appels Ruby.

Supprimez d'abord tous les fichiers de manière récursive
Seconde supprimer tous les répertoires vides

Dir.glob("./logs/**/*").each { |file| File.delete(file) if File.file? file }
Dir.glob("./logs/**/*/").each { |directory| Dir.delete(directory) }
0
HomeTurf