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

Greetings,

It's my understanding that a system() call will return zero if it was successful.

I'm doing:

unless ( system( "scp $file $target_host" ) == 0 ) { #error handling code here }
The problem is that it's returning zero on SCPs that couldn't possibly have succeded (because I'm giving it junk for $target_host).

So how can I check to see if the SCP was really successful?

Btw, yes, I know that there are better ways to do this than a system() call, but for long-winded reasons, this is what I'm stuck with. Thanks.

Replies are listed 'Best First'.
Re: Error checking on system SCP
by ikegami (Patriarch) on Dec 14, 2005 at 18:36 UTC

    That's an unsafe use of system. Using that syntax, system launches a shell to parse the command line string you're passing to system. That means you need to escape special characters $file and $target_host according to rules of whichever shell is used. But you can bypass the shell using the following syntax, since you don't use any features of the shell:

    unless ( system( 'scp', $file, $target_host ) == 0 )

    That might even solve your problem. I think the problem is that you're getting the return value of the shell that's executed to parse the command to execute instead of scp's. If you run scp directly, you'll get its error code.

      I've made the change you suggested, thanks.

      Unfortunately, it's still returning zero every time.

        Could it be that your scp doesn't return an error code?

        In Windows, I'd check it as following:

        >copy nul nul 1 file(s) copied. >if errorlevel 1 echo ** >copy bad args The system cannot find the file specified. >if errorlevel 1 echo ** **

        As you can see, copy returns an error code >= 1 when it fails. Does your scp do the same?

Re: Error checking on system SCP
by ptum (Priest) on Dec 14, 2005 at 18:27 UTC

    Perhaps you want the output from the scp command rather than the exit code? You might get better results using backticks.

    Traditionally, I've used Net::SSH's sshopen3 and Net:SCP's put to solve this problem.


    No good deed goes unpunished. -- (attributed to) Oscar Wilde
Re: Error checking on system SCP
by turo (Friar) on Dec 14, 2005 at 20:14 UTC

    i tried this way and the code runs as expected

    perl -e 'die "oops\n" unless(system("scp","test.pl","turo\@somewhere.o +ver.the.rainbow:/tldk/") == 0); print "ok\n";'
    Maybe you are not making the correct call to the scp, i mean that maybe you are calling the scp like this: scp test.pl turo@somewhere.bla.bla without specifying the directory on which it must save the file (colon and the remote directory), it will exits correctly and will create a file 'turo@somewere.bla.bla' on your current directory.
    perl -e '$site="turo\@somewhere.org"; die "oops\n" unless(system("scp" +,"test.pl",$site) == 0); print "ok\n";'

    Good luck!

    turo.

    perl -Te 'print map { chr((ord)-((10,20,2,7)[$i++])) } split //,"turo"'
      I'm not sure I follow.

      I'm just giving it junk on the path. I want it to fail. I'm trying to test my error checking.

      The problem is, I haven't gotten the code to trigger the error checking, because my test for whether or not the SCP was successful always says that it was, even if it wasn't.

        Umm (sorry, i must improve my english skills ...)

        "I'm just giving it junk on the path." It seems to be the problem. You must pass a well formed path (user@(dns-name|ip-address):/path/to/somewhere), or scp will acts as a simple 'cp' or copy.

        try this errors:

        • dns name does not exist
        • host is down
        • target directory does not exist
        • user incorrect (you must pass the password)



        Regards

        turo

        perl -Te 'print map { chr((ord)-((10,20,2,7)[$i++])) } split //,"turo"'