i'm writing a python script to execute shell command, and i'm taking arguments and i want to pass the value of that to the command
#!/usr/bin/env python
import commands
import subprocess
import sys
command = commands.getoutput('fs_cli -x "sofia profile external restart"')
this code works fine
when i try to take the argument and pass to command it fails
command = commands.getoutput('fs_cli -x "sofia profile" + sys.argv[1]
+ " restart"')
supp folks
You should write:
command = commands.getoutput('fs_cli -x "sofia profile ' + sys.argv[1] + ' restart"')
Take a look to argparse and subprocess.
One of the way to do this is to convert your command that you want to execute into string and then execute it as eval()
example :
eval(expression/command in string)
Related
I'm looking to pass variables from a Python script into variables of a Powershell script without using arguments.
var_pass_test.py
import subprocess, sys
setup_script = 'C:\\Users\\user\\Desktop\\Code\\Creation\\var_pass_test.ps1'
test1 = "Hello"
p = subprocess.run(["powershell.exe",
setup_script], test1,
stdout=sys.stdout)
var_pass_test.ps1
Write-Host $test1
How would one go about doing this such that the Powershell script receives the value of test1 from the Python script? Is this doable with the subprocess library?
To pass arguments verbatim to the PowerShell CLI, use the -File option: pass the script-file path first, followed by the arguments to pass to the script.
In Python, pass all arguments that make up the PowerShell command line as part of the first, array-valued argument:
import subprocess, sys
setup_script = 'C:\\Users\\user\\Desktop\\Code\\Creation\\var_pass_test.ps1'
test1 = "Hello"
p = subprocess.run([
"powershell.exe",
"-File",
setup_script,
test1
],
stdout=sys.stdout)
I am running below Python code & using subprocess to call one Python script. It is not able to substitute the value of ${ENVIRONMENT}.
import sys
import subprocess
#ENVIRONMENT=sys.argv[1]
ENVIRONMENT='test'
url=subprocess.check_output("python env.py ${ENVIRONMENT}", shell=True)
Use string formatting:
url = subprocess.check_output(
"python env.py {ENVIRONMENT}".format(ENVIRONMENT=ENVIRONMENT), shell=True)
or pass your command as a list:
url = subprocess.check_output(["python", "env.py", ENVIRONMENT])
Using Python's sh, I am running 3rd party shell script that requests my input (not that it matters much, but to be precise, I'm running an Ansible2 playbook with the --step option)
As an oversimplification of what is happening, I built a simple bash script that requests an input. I believe that if make this simple example work I can make the original case work too.
So please consider this bash script hello.sh:
#!/bin/bash
echo "Please input your name and press Enter:"
read name
echo "Hello $name"
I can run it from python using sh module, but it fails to receive my input...
import errno
import sh
cmd = sh.Command('./hello.sh')
for line in cmd(_iter=True, _iter_noblock=True):
if line == errno.EWOULDBLOCK:
pass
else:
print(line)
How could I make this work?
After following this tutorial, this works for my use case:
#!/usr/bin/env python3
import errno
import sh
import sys
def sh_interact(char, stdin):
global aggregated
sys.stdout.write(char)
sys.stdout.flush()
aggregated += char
if aggregated.endswith(":"):
val = input()
stdin.put(val + "\n")
cmd = sh.Command('./hello.sh')
aggregated = ""
cmd(_out=sh_interact, _out_bufsize=0)
For example, the output is:
$ ./testinput.py
Please input your name and press Enter:arod
Hello arod
There are two ways to solve this:
Using _in:
using _in, we can pass a list which can be taken as input in the python script
cmd = sh.Command('./read.sh')
stdin = ['hello']
for line in cmd(_iter=True, _iter_noblock=True, _in=stdin):
if line == errno.EWOULDBLOCK:
pass
else:
print(line)
Using command line args if you are willing to modify the script.
I'm trying to execute 10 python scripts from python code and open each of them in a new shell window.
My code :
for i in range(10):
name_of_file = "myscript"+str(i)+".py"
cmd = "python " + name_of_file
os.system("gnome-terminal -e 'bash -c " + cmd + "'")
But each script file are not executing, I get only the live interpreter of python in the new terminal...
Thank you guys
I would suggest using the subprocess module (https://docs.python.org/2/library/subprocess.html).
In this way, you'll write something like the following:
import subprocess
cmd = ['gnome-terminal', '-x', 'bash', '-c']
for i in range(10):
name_of_file = "myscript"+str(i)+".py"
your_proc = subprocess.Popen(cmd + ['python %s' % (name_of_file)])
# or if you want to use the "modern" way of formatting string you can write
# your_proc = subprocess.Popen(cmd + ['python {}'.format(name_of_file)])
...
and you have more control over the processes you start.
If you want to keep using os.system(), build your command string first, then pass it to the function. In your case would be:
cmd = 'gnome-terminal -x bash -c "python {}"'.format(name_of_file)
os.system(cmd)
something along these lines.
Thanks to #anishsane for some suggestions!
I think that it is to do with the string quoting of the argument to os.system. Try this:
os.system("""gnome-terminal -e 'bash -c "{}"'""".format(cmd))
How is it that when I write this in my terminal the file is downloaded,
curl "http://nomads.ncep.noaa.gov/cgi-bin/filter_gfs_0p50.pl?file=gfs.t00z.pgrb2full.0p50.f000&lev_10_m_above_ground=on&var_UGRD=on&var_VGRD=on&leftlon=0&rightlon=360&toplat=90&bottomlat=-90&dir=%2Fgfs.2016121900" -o "tmp_folder/gfs.t00z.pgrb2full.0p50.f000"
but using python's subprocess module, the download just hangs?
import subprocess
URL = "http://nomads.ncep.noaa.gov/cgi-bin/filter_gfs_0p50.pl?file=gfs.t00z.pgrb2full.0p50.f000&lev_10_m_above_ground=on&var_UGRD=on&var_VGRD=on&leftlon=0&rightlon=360&toplat=90&bottomlat=-90&dir=%2Fgfs.2016121900"
pipe = subprocess.Popen("curl " + URL + " -o" + " my_file", shell = True)
pipe.communicate()
What am I missing?
Thank you
The URL is probably not properly quoted, so it is interpreted by the shell (with all the & chars...)
Better run subprocess with explicit arguments as a list:
pipe = subprocess.Popen(["curl",URL,"-o","my_file"])
shell=True can probably be omitted. Since you're not using any shell capabilities, it will save you trouble.
rather than creating a Popen instance, you can just use the call method. Don't pass shell=True... just split the command with shlex so the args can be passed as a list.
import shlex
import subprocess
cmd = 'curl "http://foo.com" -o "foo.txt"'
subprocess.call(shlex.split(cmd))