Web   ·   Wiki   ·   Activities   ·   Blog   ·   Lists   ·   Chat   ·   Meeting   ·   Bugs   ·   Git   ·   Translate   ·   Archive   ·   People   ·   Donate
summaryrefslogtreecommitdiffstats
path: root/creactiweb/_templates/lib/werkzeug/script.py
diff options
context:
space:
mode:
Diffstat (limited to 'creactiweb/_templates/lib/werkzeug/script.py')
-rw-r--r--creactiweb/_templates/lib/werkzeug/script.py303
1 files changed, 303 insertions, 0 deletions
diff --git a/creactiweb/_templates/lib/werkzeug/script.py b/creactiweb/_templates/lib/werkzeug/script.py
new file mode 100644
index 0000000..efebba0
--- /dev/null
+++ b/creactiweb/_templates/lib/werkzeug/script.py
@@ -0,0 +1,303 @@
+# -*- coding: utf-8 -*-
+r'''
+ werkzeug.script
+ ~~~~~~~~~~~~~~~
+
+ Most of the time you have recurring tasks while writing an application
+ such as starting up an interactive python interpreter with some prefilled
+ imports, starting the development server, initializing the database or
+ something similar.
+
+ For that purpose werkzeug provides the `werkzeug.script` module which
+ helps you writing such scripts.
+
+
+ Basic Usage
+ -----------
+
+ The following snippet is roughly the same in every werkzeug script::
+
+ #!/usr/bin/env python
+ # -*- coding: utf-8 -*-
+ from werkzeug import script
+
+ # actions go here
+
+ if __name__ == '__main__':
+ script.run()
+
+ Starting this script now does nothing because no actions are defined.
+ An action is a function in the same module starting with ``"action_"``
+ which takes a number of arguments where every argument has a default. The
+ type of the default value specifies the type of the argument.
+
+ Arguments can then be passed by position or using ``--name=value`` from
+ the shell.
+
+ Because a runserver and shell command is pretty common there are two
+ factory functions that create such commands::
+
+ def make_app():
+ from yourapplication import YourApplication
+ return YourApplication(...)
+
+ action_runserver = script.make_runserver(make_app, use_reloader=True)
+ action_shell = script.make_shell(lambda: {'app': make_app()})
+
+
+ Using The Scripts
+ -----------------
+
+ The script from above can be used like this from the shell now:
+
+ .. sourcecode:: text
+
+ $ ./manage.py --help
+ $ ./manage.py runserver localhost 8080 --debugger --no-reloader
+ $ ./manage.py runserver -p 4000
+ $ ./manage.py shell
+
+ As you can see it's possible to pass parameters as positional arguments
+ or as named parameters, pretty much like Python function calls.
+
+
+ :copyright: (c) 2010 by the Werkzeug Team, see AUTHORS for more details.
+ :license: BSD, see LICENSE for more details.
+'''
+import sys
+import inspect
+import getopt
+from os.path import basename
+
+
+argument_types = {
+ bool: 'boolean',
+ str: 'string',
+ int: 'integer',
+ float: 'float'
+}
+
+
+converters = {
+ 'boolean': lambda x: x.lower() in ('1', 'true', 'yes', 'on'),
+ 'string': str,
+ 'integer': int,
+ 'float': float
+}
+
+
+def run(namespace=None, action_prefix='action_', args=None):
+ """Run the script. Participating actions are looked up in the caller's
+ namespace if no namespace is given, otherwise in the dict provided.
+ Only items that start with action_prefix are processed as actions. If
+ you want to use all items in the namespace provided as actions set
+ action_prefix to an empty string.
+
+ :param namespace: An optional dict where the functions are looked up in.
+ By default the local namespace of the caller is used.
+ :param action_prefix: The prefix for the functions. Everything else
+ is ignored.
+ :param args: the arguments for the function. If not specified
+ :data:`sys.argv` without the first argument is used.
+ """
+ if namespace is None:
+ namespace = sys._getframe(1).f_locals
+ actions = find_actions(namespace, action_prefix)
+
+ if args is None:
+ args = sys.argv[1:]
+ if not args or args[0] in ('-h', '--help'):
+ return print_usage(actions)
+ elif args[0] not in actions:
+ fail('Unknown action \'%s\'' % args[0])
+
+ arguments = {}
+ types = {}
+ key_to_arg = {}
+ long_options = []
+ formatstring = ''
+ func, doc, arg_def = actions[args.pop(0)]
+ for idx, (arg, shortcut, default, option_type) in enumerate(arg_def):
+ real_arg = arg.replace('-', '_')
+ if shortcut:
+ formatstring += shortcut
+ if not isinstance(default, bool):
+ formatstring += ':'
+ key_to_arg['-' + shortcut] = real_arg
+ long_options.append(isinstance(default, bool) and arg or arg + '=')
+ key_to_arg['--' + arg] = real_arg
+ key_to_arg[idx] = real_arg
+ types[real_arg] = option_type
+ arguments[real_arg] = default
+
+ try:
+ optlist, posargs = getopt.gnu_getopt(args, formatstring, long_options)
+ except getopt.GetoptError, e:
+ fail(str(e))
+
+ specified_arguments = set()
+ for key, value in enumerate(posargs):
+ try:
+ arg = key_to_arg[key]
+ except IndexError:
+ fail('Too many parameters')
+ specified_arguments.add(arg)
+ try:
+ arguments[arg] = converters[types[arg]](value)
+ except ValueError:
+ fail('Invalid value for argument %s (%s): %s' % (key, arg, value))
+
+ for key, value in optlist:
+ arg = key_to_arg[key]
+ if arg in specified_arguments:
+ fail('Argument \'%s\' is specified twice' % arg)
+ if types[arg] == 'boolean':
+ if arg.startswith('no_'):
+ value = 'no'
+ else:
+ value = 'yes'
+ try:
+ arguments[arg] = converters[types[arg]](value)
+ except ValueError:
+ fail('Invalid value for \'%s\': %s' % (key, value))
+
+ newargs = {}
+ for k, v in arguments.iteritems():
+ newargs[k.startswith('no_') and k[3:] or k] = v
+ arguments = newargs
+ return func(**arguments)
+
+
+def fail(message, code=-1):
+ """Fail with an error."""
+ print >> sys.stderr, 'Error:', message
+ sys.exit(code)
+
+
+def find_actions(namespace, action_prefix):
+ """Find all the actions in the namespace."""
+ actions = {}
+ for key, value in namespace.iteritems():
+ if key.startswith(action_prefix):
+ actions[key[len(action_prefix):]] = analyse_action(value)
+ return actions
+
+
+def print_usage(actions):
+ """Print the usage information. (Help screen)"""
+ actions = actions.items()
+ actions.sort()
+ print 'usage: %s <action> [<options>]' % basename(sys.argv[0])
+ print ' %s --help' % basename(sys.argv[0])
+ print
+ print 'actions:'
+ for name, (func, doc, arguments) in actions:
+ print ' %s:' % name
+ for line in doc.splitlines():
+ print ' %s' % line
+ if arguments:
+ print
+ for arg, shortcut, default, argtype in arguments:
+ if isinstance(default, bool):
+ print ' %s' % (
+ (shortcut and '-%s, ' % shortcut or '') + '--' + arg
+ )
+ else:
+ print ' %-30s%-10s%s' % (
+ (shortcut and '-%s, ' % shortcut or '') + '--' + arg,
+ argtype, default
+ )
+ print
+
+
+def analyse_action(func):
+ """Analyse a function."""
+ description = inspect.getdoc(func) or 'undocumented action'
+ arguments = []
+ args, varargs, kwargs, defaults = inspect.getargspec(func)
+ if varargs or kwargs:
+ raise TypeError('variable length arguments for action not allowed.')
+ if len(args) != len(defaults or ()):
+ raise TypeError('not all arguments have proper definitions')
+
+ for idx, (arg, definition) in enumerate(zip(args, defaults or ())):
+ if arg.startswith('_'):
+ raise TypeError('arguments may not start with an underscore')
+ if not isinstance(definition, tuple):
+ shortcut = None
+ default = definition
+ else:
+ shortcut, default = definition
+ argument_type = argument_types[type(default)]
+ if isinstance(default, bool) and default is True:
+ arg = 'no-' + arg
+ arguments.append((arg.replace('_', '-'), shortcut,
+ default, argument_type))
+ return func, description, arguments
+
+
+def make_shell(init_func=None, banner=None, use_ipython=True):
+ """Returns an action callback that spawns a new interactive
+ python shell.
+
+ :param init_func: an optional initialization function that is
+ called before the shell is started. The return
+ value of this function is the initial namespace.
+ :param banner: the banner that is displayed before the shell. If
+ not specified a generic banner is used instead.
+ :param use_ipython: if set to `True` ipython is used if available.
+ """
+ if banner is None:
+ banner = 'Interactive Werkzeug Shell'
+ if init_func is None:
+ init_func = dict
+ def action(ipython=use_ipython):
+ """Start a new interactive python session."""
+ namespace = init_func()
+ if ipython:
+ try:
+ import IPython
+ except ImportError:
+ pass
+ else:
+ sh = IPython.Shell.IPShellEmbed(banner=banner)
+ sh(global_ns={}, local_ns=namespace)
+ return
+ from code import interact
+ interact(banner, local=namespace)
+ return action
+
+
+def make_runserver(app_factory, hostname='localhost', port=5000,
+ use_reloader=False, use_debugger=False, use_evalex=True,
+ threaded=False, processes=1, static_files=None,
+ extra_files=None, ssl_context=None):
+ """Returns an action callback that spawns a new development server.
+
+ .. versionadded:: 0.5
+ `static_files` and `extra_files` was added.
+
+ ..versionadded:: 0.6.1
+ `ssl_context` was added.
+
+ :param app_factory: a function that returns a new WSGI application.
+ :param hostname: the default hostname the server should listen on.
+ :param port: the default port of the server.
+ :param use_reloader: the default setting for the reloader.
+ :param use_evalex: the default setting for the evalex flag of the debugger.
+ :param threaded: the default threading setting.
+ :param processes: the default number of processes to start.
+ :param static_files: optional dict of static files.
+ :param extra_files: optional list of extra files to track for reloading.
+ :param ssl_context: optional SSL context for running server in HTTPS mode.
+ """
+ def action(hostname=('h', hostname), port=('p', port),
+ reloader=use_reloader, debugger=use_debugger,
+ evalex=use_evalex, threaded=threaded, processes=processes):
+ """Start a new development server."""
+ from werkzeug.serving import run_simple
+ app = app_factory()
+ run_simple(hostname, port, app, reloader, debugger, evalex,
+ extra_files, 1, threaded, processes,
+ static_files=static_files, ssl_context=ssl_context)
+ return action