Why shouldn't I use shell tools in Perl code?

It is generally recommended to use additional linux tools in Perl code; for example, if someone intends to print the last line of a text file, he may:

$last_line = `tail -1 $file` ; 

or else, open the file and read it line by line

  open(INFO,$file); while(<INFO>) { $last_line = $_ if eof; } 

What are the pitfalls of using the previous one and why should I avoid using shell tools in my code?

thanks,

+4
source share
6 answers
  • Efficiency - You Don't Need to Create a New Process
  • Portability - you don’t need to worry that the executable does not exist, accepts different keys or has a different output
  • Ease of use - you do not need to analyze the output, the results are already in a useful form.
  • Error handling - you have finer control over errors and what to do with them in Perl.
+23
source

It’s better to save all the actions in Perl because it is faster and because it is more secure. This is faster because you are not creating a new process, and it is safer because you do not have to worry about tricking the shell meta characters.

For example, in your first case, if $file contains " afilename ; rm -rf ~ ", you would be a very unhappy camper.

PS It's best to use Perlway to use the tail of File :: ReadBackwards

+15
source

One of the main reasons (besides portability) for not executing shell commands is that it introduces overhead, creating another process. This is why many of the same features are available through CPAN in Perl modules.

+10
source

One reason is that your Perl code may work in an environment where there is no shell tool called tail.

This is a personal challenge depending on the project:

  • Will it always be used in tail shell environments?
  • Do you only care about using pure Perl code?
+9
source

Using tail ? Good. But this is indeed a special case, because it is so easy to use and because it is so trivial.

The problem as a whole is not really efficacy or tolerance, which is largely irrelevant; The problem is easy to use. To run an external utility, you need to find out what arguments it takes, write code to convert your program data structures to this format, bring them correctly, create a command line and launch the application. Then you may have to pass data in and read data from it (including complexity, such as an event loop, worry about deadlock, etc.) and finally interpret the return value. (UNIX processes consider "0" to be true and something else is false, but Perl suggests otherwise. foo() and die hard to read.) This is a lot of work, and therefore people avoid it. It is much easier to instantiate a class and call methods on it to get the data you need.

(You can abstract processes this way, for example, see Crypt :: GpgME. It handles the complexity associated with calling gpg , which usually involves creating multiple file descriptors other than STDOUT, STDIN, and STDERR, among others.)

+5
source

The main reason I see that all this does in Perl will be for reliability. Your tail usage will fail if the file name has metacharacters or shell spaces or does not exist or is not available. From Perl, the characters in the file name are not a problem, and you can distinguish errors when accessing the file. Sometimes being reliable is more important than fast coding, and sometimes not.

+4
source

All Articles