Forum: Ruby Copy all files in a directory

Announcement (2017-05-07): www.ruby-forum.com is now read-only since I unfortunately do not have the time to support and maintain the forum any more. Please see rubyonrails.org/community and ruby-lang.org/en/community for other Rails- und Ruby-related community platforms.
85dcac21f5bd12ea1e44eb070f068d2f?d=identicon&s=25 Charlie B. (charlie_b84)
on 2012-04-10 20:57
Still new to Ruby and feel silly having to ask such a simple question,
but I can't find any examples of this on the web.

I have files in Dir1.  I want to copy all the files, and only the files,
to Dir2.  I don't always know the name of them or their extensions, I
just want them all copied.

Is there really nothing as simple as xcopy c:\dir1\*.* c:\dir2 ??  I
can't find a wildcard argument under FileUtils.cp.  Am I missing the
painfully obvious solution here?
Jonathan Gold (Guest)
on 2012-04-10 21:15
(Received via mailing list)
You may well get a simpler solution (and I'll be interested to see it
myself),
but fwiw, here's how I roll with this kind of problem:

    Dir.chdir( dir1 ) do
        Dir.glob( "**/*" ).select { |f| File.file?( f ) }.each do |f|
            dest = "#{dir2}/#{f}"
            FileUtils.mkdir_p( File.dirname( dest ) )
            FileUtils.cp( f, dest )
        end
    end

It's worth having a strategy for handling failures (remove partially
copied dir2
in begin/rescue, or perhaps modify the block above to detect and remove
existing
dest files, etc)

jonathan
85dcac21f5bd12ea1e44eb070f068d2f?d=identicon&s=25 Charlie B. (charlie_b84)
on 2012-04-10 21:19
I was afraid I'd have to resort to a loop to grab each file and move it.
I'm just shocked there isn't a one line solution to this.  When your
scripting language is more difficult and cumbersome than a 20 year old
DOS command,
that's ridiculous.
Ian M. Asaff (Guest)
on 2012-04-10 21:23
(Received via mailing list)
why not use system("shell cmd")?
85dcac21f5bd12ea1e44eb070f068d2f?d=identicon&s=25 Charlie B. (charlie_b84)
on 2012-04-10 21:24
I'm leaning toward calling xcopy but I thought there would be a ruby
equivalent to it.
Steve Klabnik (Guest)
on 2012-04-10 21:29
(Received via mailing list)
> Is there really nothing as simple as xcopy c:\dir1\*.* c:\dir2 ?? I
> can't find a wildcard argument under FileUtils.cp. Am I missing the
> painfully obvious solution here?

From the docs:
http://ruby-doc.org/stdlib-1.9.3/libdoc/fileutils/...

FileUtils.cp %w(cgi.rb complex.rb date.rb), '/usr/lib/ruby/1.6'

Hence, you can pass a list of things as the first argument, and it'll
work.

FileUtils.cp Dir["dir1/*"].collect{|f| File.expand_path(f)}, "dir2"

That's the shortest way I can think of.
Steve Klabnik (Guest)
on 2012-04-10 21:33
(Received via mailing list)
Actually, since Dir.glob taks a block, I like this better:

Dir.glob("dir1/*") {|f| FileUtils.cp File.expand_path(f), "dir2" }
85dcac21f5bd12ea1e44eb070f068d2f?d=identicon&s=25 Charlie B. (charlie_b84)
on 2012-04-10 21:38
FileUtils.cp works great if you know what you want to copy and if you
have relatively few items.  If you have a folder with 50 files in it,
even if you knew their names it isn't practical to use the %w to copy
them all.
85dcac21f5bd12ea1e44eb070f068d2f?d=identicon&s=25 Charlie B. (charlie_b84)
on 2012-04-10 21:41
Steve Klabnik gets the gold star today.  Using Dir.glob this can all be
done in one line of code.  Thank you!
2245ddf5d6899af73356ef1463bbbd89?d=identicon&s=25 Alexis A. (alexis12)
on 2014-02-26 09:38
Long Path Tool deletes/unlocks, copies/renames path too long
files/folders.
9d2d160377d47a2144b12d36ab63126f?d=identicon&s=25 Regis d. (raubarede)
on 2014-02-26 15:14
Charlie B. wrote in post #1055889:
> I'm leaning toward calling xcopy but I thought there would be a ruby
> equivalent to it.

do it yourself :

class Array
   def xcopy(dir2)
      FileUtils.cp(self,dir2)
      self.size
   end
end

and then

 Dir["*.rb"].xcopy("d:/save")
13d0171c6ee97074d61f182a6e3a9f4e?d=identicon&s=25 Robert K. (robert_k78)
on 2014-03-03 17:45
(Received via mailing list)
On Tue, Apr 10, 2012 at 9:42 PM, Charlie B. <lists@ruby-forum.com>
wrote:
> Steve Klabnik gets the gold star today.  Using Dir.glob this can all be
> done in one line of code.  Thank you!

That solution has two issues:
1. It does not filter by type.
2. It unnecessarily expands the path.

FileUtils.cp Dir["dir1/*"].select {|f| test ?f, f}, "dir2"

Or, with Pathname

FileUtils.cp Pathname.glob("dir1/*").select(&:file?), "dir2"

Cheers

robert
This topic is locked and can not be replied to.