What I want to do is very simple but I can't figure out a good and not too complex solution for this. Basically I want to define some global variables that will be used for example as a folder name
global folder = "C:\\TEMP\\" + foldername
And what I want is to set the foldername value as input when running the script, something like:
python myscript.py --folder somebeautifulfoldername
so when running my script, the folder will become C:\TEMP\somebeautifulfoldername
You can pass arguments to Python script like following:
python test.py arg1 arg2 arg3
And this is what you get
Argument List: ['test.py', 'arg1', 'arg2', 'arg3']
In your case:
python myscript.py somebeautifulfoldername
folder = "C:\\TEMP\\" + sys.argv[1]
You can use the built-in argparse module for this combined with getting the command line arguments from sys.argv:
import argparse
import sys
if __name__ == '__main__':
parser = argparse.ArgumentParser(description = 'My script')
parser.add_argument('--folder', help = "Subfolder of C:\TEMP\ to manipulate")
args = parser.parse_args(sys.argv[1:])
folder = "C:\\TEMP\\"+args.folder
print folder
Here I added just a very simple argument with some basic help string, but you can do quite a lot with this like giving a default value, allowing a list of files instead of a single file, specify the type, ... . See the manual for more details and examples.
Usage:
>python myscript.py --folder somebeautifulfoldername
C:\TEMP\somebeautifulfoldername
>python myscript.py --help
usage: tmp.py [-h] [--folder FOLDER]
My script
optional arguments:
-h, --help show this help message and exit
--folder FOLDER Subfolder of C:\TEMP\ to manipulate
import sys
folder = "none"
if("--folder" in sys.argv):
folder = sys.argv[sys.argv.index("--folder") + 1]
print folder
If you run it the way you want:
python myscript.py --folder "HELLOFOLDER"
It will give: HELLOFOLDER
There are a number of options to parse command line arguments into a Python script. There's the standard library's optparse and argparse for instance.
A really nice 3rd party tool is docopt, which allows you to write the logic described above very easily by describing the script usage directly as documentation of your script like this:
"""My script
Usage:
myscript.py --folder=<folder>
Options:
-h --help Show this screen.
--version Show version.
--folder=<folder> Choose folder.
"""
from docopt import docopt
if __name__ == '__main__':
arguments = docopt(__doc__, version='myscript 1.0')
folder = "C:\\TEMP\\" + arguments["--folder"]
print(folder)
That said, you may also want to look into tempfile for generating temporary files to make the script more cross-platform. Hard-coding Windows-specific paths is rarely a good idea.
Related
I'm a pretty novice programmer.
I'm trying to figure out how to make it so that a python script takes an input when it's called in command prompt and has a default when no input is present.
Basically it's a program that would run one way by default C:Program Files\Sample\Sample.exe and a different way if you do something like C:Program Files\Sample\Sample.exe "option 2". Is this possible?
Is there something in python that I have to do or in the conversion from .py to .exe? I'm using pyinstaller to convert the script.
Thank you in advance and sorry if this isn't very professionally asked.
Have you looked into sys.argv? It contains the command line arguments, and the first value is the program itself.
import sys
thing = "default"
if len(sys.argv) > 1:
thing = sys.argv[1]
print("Thing is: ", thing)
Run like this:
$ python3.7 ex.py
Thing is: default
$ python3.7 ex.py a
Thing is: a
You could also use the argparse module, which offers more flexibility:
import argparse
parser = argparse.ArgumentParser(description='Example.')
parser.add_argument('thing', type=str, nargs="?", default="default")
args = parser.parse_args()
print("Thing is", args.thing)
Which produces the same result:
$ python3.7 ex.py
Thing is default
$ python3.7 ex.py a
Thing is a
You could also use the click library, which provides even more flexibility:
import click
#click.command()
#click.argument('thing', default="default")
def program(thing):
print("Thing is", thing)
if __name__ == '__main__':
program()
Same thing:
$ python3.7 ex.py
Thing is default
$ python3.7 ex.py a
Thing is a
A Simple Example
#!/usr/bin/python
import sys
def program(arguments):
if arguments:
for arg in arguments:
print(arg + '\n')
else:
print('no arguments')
if __name__ == "__main__":
program(sys.argv[1:])
I am doing some practice Python exercises and I found one which is asking to create a Python module with various functions. I created a Python package and implemented the functions. So far so good, but a request is that if you call the module with the argument "-h", the message "Help" will be displayed, if the module is being imported, nothing is being displayed. How can we do this, is there any default function that needs to be overwritten? I'm not sure on how can we call a module, I thought we just use a package to better encapsulate our methods
Many thanks and sorry for being noob
Python is an interpreted language, that just starts with the top-level source code no main function, you might have seen in other languages. Files to be imported are written exactly the same way. All of the code, that is outside of functions is executed.
e.g.
myscript.py
def fn(a, b):
return a+b
print(fn(1, 1))
This as a fully working program, printing out the answer to, how much is 1+1. But what if you would like to import it to use the fn function inside another script? Doing import myscript would print 2 (and then finally provide you the fn function). The workaround is checking for __name__ == '__main__': inside myscript.py, which will evaluate to true, when being executed only (e.g. python myscript.py). It will be false otherwise (import myscript).
See the related Q&A.
Reference: https://docs.python.org/2/howto/argparse.html
$ cat sample.py
import argparse
parser = argparse.ArgumentParser()
parser.add_argument("--foo", help="sample argument", action="store", dest='foo')
args = parser.parse_args()
if args.foo:
print("foo = {}".format(args.foo))
$ python sample.py --help
$ python sample.py --help
usage: sample.py [-h] [--foo FOO]
optional arguments:
-h, --help show this help message and exit
--foo FOO sample argument
$
$ python sample.py --foo argument_value
$ python sample.py --foo bar
foo = bar
$ python sample.py --foo=10
foo = 10
$
So to be more precise, what I am trying to do is :
read a full shell command as argument of my python script like : python myPythonScript.py ls -Fl
Call that command within my python script when I'd like to (Make some loops on some folders and apply the command etc ...)
I tried this :
import subprocess
from optparse import OptionParser
from subprocess import call
def execCommand(cmd):
call(cmd)
if __name__ == '__main__':
parser = OptionParser()
(options,args) = parser.parse_args()
print args
execCommand(args)
The result is that now I can do python myPythonScript.py ls , but I don't know how to add options. I know I can use parser.add_option , but don't know how to make it work for all options as I don't want to make only specific options available, but all possible options depending on the command I am running.
Can I use something like parser.add_option('-*') ? How can I parse the options then and call the command with its options ?
EDIT
I need my program to parse all type of commands passed as argument : python myScript.py ls -Fl , python myScript.py git pull, python myScript rm -rf * etc ...
OptionParser is useful when your own program wants to process the arguments: it helps you turn string arguments into booleans or integers or list items or whatever. In your case, you just want to pass the arguments on to the program you're invoking, so don't bother with OptionParser. Just pass the arguments as given in sys.argv.
subprocess.call(sys.argv[1:])
Depending on how much your program depends on command line arguments, you can go with simple route.
Simple way of reading command line arguments
Use sys to obtain all the arguments to python command line.
import sys
print sys.argv[1:]
Then you can use subprocess to execute it.
from subprocess import call
# e.g. call(["ls", "-l"])
call(sys.argv[1:])
This sample below works fine for me.
import sys
from subprocess import call
print(sys.argv[1:])
call(sys.argv[1:])
Is it possible to run a python script with parameters in command line like this:
./hello(var=True)
or is it mandatory to do like this:
python -c "from hello import *;hello(var=True)"
The first way is shorter and simpler.
Most shells use parentheses for grouping or sub-shells. So you can't call any commands like command(arg) from a normal shell ...but you can write a python script (./hello.py) that takes an argument.
import optparse
parser = optparse.OptionParser()
parser.add_option('-f', dest="f", action="store_true", default=False)
options, remainder = parser.parse_args()
print ("Flag={}".format(options.f))
And the call it with python hello.py -f
./hello(var=True) would be impossible from REPL shell. In some case it could be useful to have python function available in your current shell session. Here a workaround to make your python functions available in your shell environment.
# python-tools.sh
#!/usr/bin/env bash
set -a # make all available export all variable)
function hello(){
cd "/app/python/commands"
python "test.py" $#
}
Content of the python script
#! /usr/bin/env python
# /app/python/commands/test.py script
import sys
def test(*args):
print(args)
if __name__ == '__main__':
if sys.argv[1] in globals().keys():
print(sys.argv[1])
globals()[sys.argv[1]](sys.argv[2:])
else:
print("%s Not known function" % sys.argv[1])
Then source python-tools.sh
source python-tools.sh
After the hello function is available
$ hello test arg2 arg2
test
(['arg2', 'arg2'],)
How can I make a command line, so I can execute my program on Windows with some parameters...
For example:
C:/Program/App.exe -safemode
have a look at the getopt and optparse modules from the standard lib, many good things could be also said about more advanced argparse module.
Generally you just need to access sys.argv.
I sense that you also want to generate an 'executable' that you can run standalone.... For that you use py2exe
Here is a complete example.py:
import optparse
parser = optparse.OptionParser()
parser.add_option("-s", "--safemode",
default = False,
action = "store_true",
help = "Should program run in safe mode?")
parser.add_option("-w", "--width",
type = "int",
default = 1024,
help = "Desired screen width in pixels")
options, arguments = parser.parse_args()
if options.safemode:
print "Proceeding safely"
else:
print "Proceeding dangerously"
if options.width == 1024:
print "running in 1024-pixel mode"
elif options.width == 1920:
print "running in 1920-pixel mode"
And here is a complete setup.py that will turn the above example.py into example.exe (in the dist subdirectory):
from distutils.core import setup
import py2exe
import sys
sys.argv.append('py2exe')
setup(
options = {'py2exe': dict(bundle_files=1, optimize=2)},
console = ["example.py"],
zipfile = None,
)
Are you speaking about parameter passed to a python script?
'couse you can access them by
import sys
print sys.argv
Or can use a more sophisticated getopt module.
Not a python guy (yet anyway) but my Google-fu found this assuming you meant "handling command line arguments":
http://www.faqs.org/docs/diveintopython/kgp_commandline.html
Use optparse.OptionParser.
from optparse import OptionParser
import sys
def make_cli_parser():
"""Makes the parser for the command line interface."""
usage = "python %prog [OPTIONS]"
cli_parser = OptionParser(usage)
cli_parser.add_option('-s', '--safemode', action='store_true',
help="Run in safe mode")
return cli_parser
def main(argv):
cli_parser = make_cli_parser()
opts, args = cli_parser.parse_args(argv)
if opts.safemode:
print "Running in safe mode."
else:
print "Running with the devil."
if __name__ == '__main__':
main(sys.argv[1:])
In use:
$ python opt.py
Running with the devil.
$ python opt.py -s
Running in safe mode.
$ python opt.py -h
Usage: python opt.py [OPTIONS]
Options:
-h, --help show this help message and exit
-s, --safemode Run in safe mode
Or are you just asking how to open a command line?
go to the start menu, click "run" (or just type, in Windows 7), type "cmd"
This will open up a command shell.
Given that your question is tagged python, I'm not sure it's going to be compiled into an exe, you might have to type "python (your source here).py -safemode".
The other comments addressed how to handle parameters. If you want to make your python program an exe you might want to look at py2exe.
This is not required but you mentioned App.exe and not App.py
You are asking a question that has several levels of answers.
First, command line is passed into the array sys.argv. argv is a historic name from C and Unix languages. So:
~/p$ cat > args.py
import sys
print "You have ", len(sys.argv), "arguments."
for i in range(len(sys.argv)):
print "argv[", i, "] = ", sys.argv[i]
~/p$ python args.py 34 2 2 2
You have 5 arguments.
argv[ 0 ] = args.py
argv[ 1 ] = 34
argv[ 2 ] = 2
argv[ 3 ] = 2
argv[ 4 ] = 2
This works both in MS Windows and Unix.
Second, you might be asking "How do I get nice arguments? Have it handle /help in
MS Windows or --help in Linux?"
Well, there are three choices which try to do what you want. Two, optparse and getopt are already in the standard library, while argparse is on its way. All three of these are libraries that start with the sys.argv array of strings, a description of you command line arguments, and return some sort of data structure or class from which
you can get the options you mean.
getopt does the minimal job. It does not provide "/help" or "--help".
optparse does a more detailed job. It provides "/help" and both short and long
versions of options, e.g., "-v" and "--verbose".
argparse handles the kitchen sink, including "/help", short and long commands,
and also subcommand structures, as you see in source control "git add ....", and
positional arguments.
As you move to the richer parsing, you need to give the parser more details about what you want the command line arguments to be. For example, you need to pass a long written
description of the argument if you want the --help argument to print it.
Third, you might be asking for a tool that just deals with the options from the command
line, environment variables and configuration files. Python currently has separate tools
for each of these. Perhaps I'll write a unified one, You will need:
- Command line arguments parsed by argparse, or getopt, etc.
- Environment variables, from os.environ[]
- Configuration files from ConfigFile or plistlib, etc.
and build your own answer to "what are the settings"?
Hope this fully answers your questions
One of the many ways:
import sys
print sys.argv
>>>python arg.py arg1 arg2
['arg.py', 'arg1', 'arg2']
sys.argv is a list containing all the arguments (also the name of script/program) as string.