http://www.perlmonks.org?node_id=804509

puterboy has asked for the wisdom of the Perl Monks concerning the following question:

I would like to copy files preserving attributes (something like cp -cdpP) within perl rather than using a system call to *nix 'cp'.

Now from the documentation of File::Copy, it seems that this module won't do that for me at least on *nix since there is no syscopy routine.

I also saw an old thread (Circa 2003) saying that since the potential attributes to be preserved are not well-defined across systems (and may change in the future), this functionality has not been implemented in CPAN.

So, I ask is that still true?

Is there any (easy) way other than forking a syscall to preserve the following attributes:

timestamps ownership permissions SELinux Other ACL/extended attributes

Replies are listed 'Best First'.
Re: Copy preserving attributes
by ikegami (Patriarch) on Nov 02, 2009 at 18:10 UTC

    I would like to copy files preserving attributes (something like cp -cdpP) within perl rather than using a system call to *nix 'cp'.

    Calling cp is your best option. It can be done safely with multi-arg system

    my $rv = system('cp', '-cdpP', ...); $rv == -1 and die("Can't execute cp: $!\n"); $rv & 0x7F and die("cp died from signal ", ($rv & 0x7F), "\n"); $rv >> 8 and die("Error ", ($rv >> 8), "from cp\n");
Re: Copy preserving attributes
by thunders (Priest) on Nov 02, 2009 at 17:32 UTC

    Which version of Perl and File::Copy are you using? In CPAN File::Copy does indeed provided a syscopy.

    Update: sorry read the docs and you are correct. On UNIX syscopy is just an alias to File::Copy::copy() Here's a thread with the same essential question.

      Yes - that was exactly the thread from 2003 that I was alluding to. But since it has been 6+ years, I was wondering whether there were any new approaches or solutions... One can always hope...
Re: Copy preserving attributes
by keszler (Priest) on Nov 02, 2009 at 18:24 UTC
      any solution for extended attributes/ACLs? Or is that too system specific.

      Also, how does the efficiency of a single cp system call compare to the code you would have to read and then set timestamp/ownership/permissions internally in perl?

        Considering that the running time of the 'cp' is most likely to be bound by disk I/O, I wouldn't worry about the overhead of calling 'cp'.

        Specially if you have the need to take care of system specifics (like extended attributes/ACLs), I would prefer calling the systems 'cp' then doing it all yourself. Specially if you don't have access to all the environments the program is supposed to run in.

Re: Copy preserving attributes
by zentara (Archbishop) on Nov 02, 2009 at 18:58 UTC
Re: Copy preserving attributes
by stefbv (Curate) on Nov 02, 2009 at 18:00 UTC
    Maybe Sysadm::Install can do the job.
Re: Copy preserving attributes
by djp (Hermit) on Nov 03, 2009 at 09:41 UTC
    I've used File-Rsync with the --archive option set to achieve this. Not the most elegant solution, but it will do what you want.
      Interesting idea, but I imagine that calling rsync even if coded all in Perl will be *slower* than a 'cp' system call.