Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to copy a directory structure in ruby, excluding certain file extensions

Tags:

scripting

ruby

I want to write a ruby script to recursively copy a directory structure, but exclude certain file types. So, given the following directory structure:

folder1
  folder2
    file1.txt
    file2.txt
    file3.cs
    file4.html
  folder2
  folder3
    file4.dll

I want to copy this structure, but exlcude .txt and .cs files. So, the resulting directory structure should look like this:

folder1
  folder2
    file4.html
  folder2
  folder3
    file4.dll
like image 912
Mike Pond Avatar asked Apr 02 '09 19:04

Mike Pond


2 Answers

You could use the find module. Here's a code snippet:


require "find"

ignored_extensions = [".cs",".txt"]

Find.find(path_to_directory) do |file|
  # the name of the current file is in the variable file
  # you have to test it to see if it's a dir or a file using File.directory?
  # and you can get the extension using File.extname

  # this skips over the .cs and .txt files
  next if ignored_extensions.include?(File.extname(file))
  # insert logic to handle other type of files here
  # if the file is a directory, you have to create on your destination dir
  # and if it's a regular file, you just copy it.
end
like image 56
Geo Avatar answered Oct 18 '22 04:10

Geo


I'm not sure what your starting point is, or what you mean by manually walking, but assuming you're iterating over a collection of files, you can use the reject method to exclude items based on the evaluation of a boolean condition.

example:

Dir.glob( File.join('.', '**', '*')).reject {|filename| File.extname(filename)== '.cs' }.each {|filename| do_copy_operation filename destination}

In this example, Glob returns an enumerable collection of filenames (including directories). You exclude the items that you don't want in the reject filter. You'll then implement a method that takes a filename and a destination to do the copy.

You can use the array method include? in the reject block also, along the lines of the Find example from Geo.

Dir.glob( File.join('.', '**', '*')).reject {|file| ['.cs','.txt'].include?(File.extname(file)) }
like image 30
JasonTrue Avatar answered Oct 18 '22 04:10

JasonTrue