command not found using line in argument to os.system using python
The *
has nothing to do with the problem; the string you're substituting with %s
ends with a newline, and that newline is what breaks your code.
When you use os.popen('...').read()
, you get the entire output of ...
-- including the trailing newline, which shell command substitutions implicitly trim.
The best answer would be to rewrite your logic in Python, but the easy answer here is to use such a command substitution, which also avoids trying to pass values into a script via string substitution (which is a fast route to shell-injection security bugs):
shell_script = r'''
cur_date=$(date -d '-1 day' '+%Y%m%d')
zgrep "919535144580" /var/tmp/comp?/emse_revres_rdc.log."$cur_date"* \
| grep -v "RI" \
| cut -d "|" -f 9,10,23,24,26 \
| sort \
| uniq -c \
| sort -nr \
>> /var/tmp/Andy/test.txt
'''
os.system(shell_script)
That said, if you're just going for the shortest change possible, put the following before your original code's os.system()
call:
cur_date = cur_date.rstrip('\n')
os.system command not found after string formatting
Apart from os.system
being by way inferior to subprocess
, the likely problem is the substitution process done by .format()
.
Instead of your code, you should try
BOOT_VOLUME_ATTACHMENT_ID = "123"
print(repr('oci compute boot-volume-attachment detach --force --wait-for-state DETACHED --boot-volume-attachment-id {0} --region region1'.format(BOOT_VOLUME_ATTACHMENT_ID)))
and look what it outputs.
This will tell you if there is something strange (e. g. a line break) before the --region
.
After your question update, it becomes clear that your BOOT_VOLUME_ATTACHMENT_ID
isn't what you claimed it to be. Instead, it contains the output of a different program, which in most cases adds a line break at the end.
If you take that content and plug it into a string the way you did, this line break gets transferred into the destination string, telling the shell to execute two commands.
The solution is to use .strip()
immediately after the os.popen()
call.
About subprocess:
Your program will become cleaner (e. g. less injection-prone) if you do
import subprocess
BOOT_VOLUME_ATTACHMENT_ID = "123"
subprocess.call(['oci', 'compute', 'boot-volume-attachment', 'detach', '--force', '--wait-for-state', 'DETACHED', '--boot-volume-attachment-id', BOOT_VOLUME_ATTACHMENT_ID, '--region', 'region1'])
The reason is that this avoids having the shell between your program and oci
, thus eliminating one potential source of errors.
Trouble passing arguments into os.system()
You should call it with just one string as follows:
os.system('python main.py input laska.png output laska_save{}.png'.format(i))
The os.system
documentation says it just take an string as argument, so you must create that full string with the command before passing it to the function.
Passing arguments into os.system
Don't use os.system()
; subprocess
is definitely the way to go.
Your problem though is that you expect Python to understand that you want to interpolate args.fileread
into a string. As great as Python is, it is not able to read your mind like that!
Use string formatting instead:
os.system("rtl2gds -rtl={args.fileread} -rtl_top={args.module_name} -syn".format(args=args)
If you want to pass a filename to another command, you should not use the FileType
type option! You want a filename, not an open file object:
parser.add_argument('fileread', help='Enter the file path')
But do use subprocess.call()
instead of os.system()
:
import subprocess
subprocess.call(['rtl2gds', '-rtl=' + args.fileread, '-rtl_top=' + args.module_name, '-syn'])
If rtl2gds
implements command line parsing properly, the =
is optional and you can use the following call instead, avoiding string concatenation altogether:
subprocess.call(['rtl2gds', '-rtl', args.fileread, '-rtl_top', args.module_name, '-syn'])
How do I execute a program or call a system command?
Use the subprocess
module in the standard library:
import subprocess
subprocess.run(["ls", "-l"])
The advantage of subprocess.run
over os.system
is that it is more flexible (you can get the stdout
, stderr
, the "real" status code, better error handling, etc...).
Even the documentation for os.system
recommends using subprocess
instead:
The
subprocess
module provides more powerful facilities for spawning new processes and retrieving their results; using that module is preferable to using this function. See the Replacing Older Functions with the subprocess Module section in thesubprocess
documentation for some helpful recipes.
On Python 3.4 and earlier, use subprocess.call
instead of .run
:
subprocess.call(["ls", "-l"])
Python: Failing to open a file using os.system()
You can avoid (potential) problems with quoting, escaping, and so on, with subprocess
:
import subprocess
subprocess.call(['pdftk', '1.pdf', '2.pdf', 'cat', 'output', 'result.pdf'])
It's just as easy to use as os.system
, and even easier if you are building the argument list dynamically.
Related Topics
Python Threading with Queue: How to Avoid to Use Join
Can't Start Foreman in Heroku Tutorial Using Python
Why Is My Pygame Application Loop Not Working Properly
Convert Pyspark String to Date Format
How to Limit Execution Time of a Function Call
Create Pandas Dataframe from a String
Handling Very Large Numbers in Python
Freezing/Hanging Tkinter Gui in Waiting for the Thread to Complete
Creating a Range of Dates in Python
Check If One Package Is Installed in My System with Python
Distributing Ruby/Python Desktop Apps
Understanding the Map Function
Why Is the Pygame Animation Is Flickering
Formatting Floats Without Trailing Zeros
Runtimeerror on Windows Trying Python Multiprocessing