in one of the project I am working with, we were using backtip approach to run system commands.
resp = `7z x #{zip_file_path} -p#{password} -o#{output_path}`
which works fine. But since it might lead to command injection vulnerability we are planning to use exec or open3. With open3 we are facing issue in executing system commands. We referred this to resolve command injection.
stdin, stdout, stderr = Open3.popen3("7z", "x", zip_file_path, "-p", password, "-o", output_path)
But this leads to below error
error = stderr.readlines
# ["\n", "\n", "Command Line Error:\n", "Too short switch:\n", "-o\n"]
This works when I include params like this.
stdin, stdout, stderr = Open3.popen3("7z", "x", zip_file_path, "-p#{password}", "-o#{output_path}")
But shouldn't we pass arguments separately to avoid command injection? Or Am I doing anything wrong with first version?
Your second version (the one that works):
is perfectly safe. There's no shell involved so there's nothing that will interpret
passwordandoutput_pathother than7zitself.Unfortunately
7zhas a strange way of parsing switches. Normally you'd expect to pass arguments to switches by saying-p xyzand-pxyzwould be a short form of-p -x -y -z. When you say:that's like saying this in the shell:
but
7zdoesn't like those spaces, it wants:so you're stuck doing a bit of string interpolation. Even so, there's no shell involved with
Open3so no injection.