mirror of
https://github.com/datafolklabs/cement.git
synced 2026-02-06 11:16:46 +00:00
documentation cleanup
This commit is contained in:
parent
fb614fc8ad
commit
625e15a8a5
2
LICENSE
2
LICENSE
@ -1,4 +1,4 @@
|
||||
MODIFIED PYTHON SOFTWARE FOUNDATION LICENSE VERSION 2
|
||||
PYTHON SOFTWARE FOUNDATION LICENSE VERSION 2
|
||||
--------------------------------------------
|
||||
|
||||
1. This LICENSE AGREEMENT is between William J. Dierkes (a.k.a "BJ Dierkes"),
|
||||
|
||||
12
README
12
README
@ -6,7 +6,7 @@ DESCRIPTION:
|
||||
|
||||
Cement is an advanced CLI Application Framework for Python. It promotes code
|
||||
re-use by way of plugins and helper libraries that can be shared between
|
||||
any application built on cement. The MVC and overall framework design is
|
||||
any application built on Cement. The MVC and overall framework design is
|
||||
very much inspired by the TurboGears2 web framework. Its goal is to introduce
|
||||
a standard, and feature-full platform for both simple and complex command line
|
||||
applications as well as support rapid development needs without sacrificing
|
||||
@ -35,11 +35,11 @@ plugin system is designed to allow portability of re-usable code, and it
|
||||
is encouraged to contribute any plugins back to the project to extend the
|
||||
functionality of Cement.
|
||||
|
||||
The Cement CLI Application Framework for Python is Open Source and is
|
||||
distributed under the Python Software Foundation License. When creating
|
||||
plugins specifically for re-use within the community, please be sure to
|
||||
follow the standard naming convention "HelloWorld Plugin for Cement" as an
|
||||
example. The actual module name should be 'cement.plugins.helloworld'.
|
||||
The Cement CLI Application Framework is Open Source and is distributed under
|
||||
the Python Software Foundation License. When creating plugins specifically
|
||||
for re-use within the community, please be sure to follow the standard naming
|
||||
convention "HelloWorld Plugin for Cement" as an example. The actual module
|
||||
name should be 'cement.plugins.helloworld'.
|
||||
|
||||
|
||||
GETTING STARTED:
|
||||
|
||||
@ -14,38 +14,35 @@ from cement.core.hook import register_hook, define_hook, run_hooks
|
||||
log = get_logger(__name__)
|
||||
|
||||
def register_default_hooks():
|
||||
"""Register Cement framework hooks."""
|
||||
"""Registers Cement framework hooks."""
|
||||
define_hook('options_hook')
|
||||
define_hook('post_options_hook')
|
||||
define_hook('validate_config_hook')
|
||||
define_hook('pre_plugins_hook')
|
||||
define_hook('post_plugins_hook')
|
||||
|
||||
def lay_cement(default_app_config=None, version_banner=None):
|
||||
def lay_cement(config=None, banner=None):
|
||||
"""
|
||||
Primary method to setup an application for Cement.
|
||||
|
||||
Arguments:
|
||||
|
||||
config => dict containing application config.
|
||||
version_banner => Option txt displayed for --version
|
||||
Keyword arguments:
|
||||
config -- Dict containing application config.
|
||||
banner -- Optional text to display for --version
|
||||
"""
|
||||
vb = version_banner
|
||||
if not version_banner:
|
||||
vb = """%s version %s""" % (
|
||||
default_app_config['app_name'],
|
||||
get_distribution(default_app_config['app_egg_name']).version
|
||||
)
|
||||
if not banner:
|
||||
banner = "%s version %s" % (
|
||||
config['app_name'],
|
||||
get_distribution(config['app_egg_name']).version)
|
||||
|
||||
namespace = CementNamespace(
|
||||
label = 'global',
|
||||
version = get_distribution(default_app_config['app_egg_name']).version,
|
||||
required_api = CEMENT_API,
|
||||
config = get_default_config(),
|
||||
version_banner = vb,
|
||||
label='global',
|
||||
version=get_distribution(config['app_egg_name']).version,
|
||||
required_api=CEMENT_API,
|
||||
config=get_default_config(),
|
||||
banner=banner,
|
||||
)
|
||||
define_namespace('global', namespace)
|
||||
namespaces['global'].config.update(default_app_config)
|
||||
namespaces['global'].config.update(config)
|
||||
|
||||
register_default_hooks()
|
||||
|
||||
|
||||
@ -12,18 +12,24 @@ from cement.core.exc import CementArgumentError
|
||||
log = get_logger(__name__)
|
||||
|
||||
# FIXME: This method is so effing ugly.
|
||||
def run_command(command_name):
|
||||
def run_command(cmd_name=None):
|
||||
"""
|
||||
Run the command or namespace-subcommand.
|
||||
Run the command or namespace-subcommand as defined by the 'expose()'
|
||||
decorator used on a Controller function.
|
||||
|
||||
Keyword arguments:
|
||||
cmd_name -- The command name as store in the global 'namespaces'. For
|
||||
example, namespaces['global'].commands['cmd_name'].
|
||||
|
||||
"""
|
||||
log.debug("processing passed command '%s'", command_name)
|
||||
command_name = command_name.rstrip('*')
|
||||
if command_name in namespaces.keys():
|
||||
namespace = command_name
|
||||
log.debug("processing passed command '%s'", cmd_name)
|
||||
cmd_name = cmd_name.rstrip('*')
|
||||
if cmd_name in namespaces.keys():
|
||||
namespace = cmd_name
|
||||
else:
|
||||
namespace = 'global'
|
||||
|
||||
m = re.match('(.*)-help', command_name)
|
||||
m = re.match('(.*)-help', cmd_name)
|
||||
if m and m.group(1) in namespaces.keys():
|
||||
namespace = m.group(1)
|
||||
raise CementArgumentError, \
|
||||
@ -46,7 +52,7 @@ def run_command(command_name):
|
||||
pass # doesn't expect a result
|
||||
|
||||
if namespace == 'global':
|
||||
actual_cmd = command_name
|
||||
actual_cmd = cmd_name
|
||||
else:
|
||||
try:
|
||||
actual_cmd = cli_args[1]
|
||||
@ -62,4 +68,4 @@ def run_command(command_name):
|
||||
log.debug("executing command '%s'" % actual_cmd)
|
||||
func(cli_opts, cli_args)
|
||||
else:
|
||||
raise CementArgumentError, "Unknown command, see --help?"
|
||||
raise CementArgumentError, "Unknown command '%s', see --help?" % actual_cmd
|
||||
@ -7,9 +7,26 @@ from cement.core.opt import init_parser
|
||||
|
||||
class CementNamespace(object):
|
||||
"""
|
||||
Class that handles plugins and namespaces (commands, options, hooks).
|
||||
Class that handles plugins and namespaces.
|
||||
"""
|
||||
def __init__(self, label, version, required_api, **kw):
|
||||
"""
|
||||
Initialize CementNamespace class.
|
||||
|
||||
Required arguments:
|
||||
label -- Namespace label. Class is stored in the global
|
||||
'namespaces' dict as namespaces['label'].
|
||||
version -- The version of the application.
|
||||
required_api-- The required Cement API the application was built on.
|
||||
|
||||
Optional keyword arguments:
|
||||
description -- Description of the plugin/namespace (default: '')
|
||||
commands -- A dict of command functions (default: {})
|
||||
is_hidden -- Boolean, whether command should display in --help
|
||||
output (default: False)
|
||||
config -- A config dict (default: None)
|
||||
banner -- A version banner to display for --version (default: '')
|
||||
"""
|
||||
self.label = label
|
||||
self.version = version
|
||||
self.required_api = required_api
|
||||
@ -21,20 +38,20 @@ class CementNamespace(object):
|
||||
if kw.get('config', None):
|
||||
self.config.update(kw['config'])
|
||||
|
||||
if not kw.get('version_banner'):
|
||||
vb = "%s version %s" % (self.label, self.version)
|
||||
if not kw.get('banner'):
|
||||
banner = "%s version %s" % (self.label, self.version)
|
||||
else:
|
||||
vb = kw.get('version_banner')
|
||||
self.options = kw.get('options', init_parser(version_banner=vb))
|
||||
banner = kw.get('banner')
|
||||
self.options = kw.get('options', init_parser(banner=banner))
|
||||
|
||||
def define_namespace(namespace, namespace_obj):
|
||||
"""
|
||||
Define a namespace for commands, options, configuration, etc.
|
||||
|
||||
Arguments:
|
||||
|
||||
namespace => label of the namespace
|
||||
namespace_obj => CementNamespace object
|
||||
Keyword arguments:
|
||||
namespace -- Label of the namespace
|
||||
namespace_obj -- CementNamespace object. Stored in global 'namespaces'
|
||||
dict as namespaces['namespace']
|
||||
"""
|
||||
if namespaces.has_key(namespace):
|
||||
raise CementRuntimeError, "Namespace '%s' already defined!" % namespace
|
||||
|
||||
@ -38,12 +38,18 @@ class Options(object):
|
||||
self.parser = OptionParser(formatter=fmt, version=version_banner)
|
||||
|
||||
|
||||
def init_parser(version_banner=None):
|
||||
"""Create an OptionParser object and returns its parser member."""
|
||||
def init_parser(banner=None):
|
||||
"""
|
||||
Create an OptionParser object and returns its parser member.
|
||||
|
||||
Keyword arguments:
|
||||
banner -- Optional version banner to display for --version
|
||||
|
||||
"""
|
||||
fmt = IndentedHelpFormatter(
|
||||
indent_increment=4, max_help_position=32, width=77, short_first=1
|
||||
)
|
||||
parser = OptionParser(formatter=fmt, version=version_banner)
|
||||
parser = OptionParser(formatter=fmt, version=banner)
|
||||
return parser
|
||||
|
||||
|
||||
|
||||
@ -132,7 +132,6 @@ def load_all_plugins():
|
||||
elif opt.get_opt_string() == '--json':
|
||||
pass
|
||||
else:
|
||||
print opt
|
||||
namespaces[namespace].options.add_option(opt)
|
||||
|
||||
for res in run_hooks('post_plugins_hook'):
|
||||
|
||||
@ -29,7 +29,7 @@ def main():
|
||||
# Warning: You shouldn't modify below this point unless you know what
|
||||
# you're doing.
|
||||
|
||||
lay_cement(default_config, version_banner=BANNER)
|
||||
lay_cement(config=default_config, banner=BANNER)
|
||||
|
||||
log = get_logger(__name__)
|
||||
log.debug("Cement Framework Initialized!")
|
||||
|
||||
@ -21,11 +21,11 @@ class {{package}}Plugin(CementPlugin):
|
||||
|
||||
def __init__(self):
|
||||
CementPlugin.__init__(self,
|
||||
label = '{{package}}',
|
||||
version = VERSION,
|
||||
description = 'Core plugin for {{package}}',
|
||||
required_api = REQUIRED_CEMENT_API,
|
||||
version_banner = BANNER,
|
||||
label='{{package}}',
|
||||
version=VERSION,
|
||||
description='Core plugin for {{package}}',
|
||||
required_api=REQUIRED_CEMENT_API,
|
||||
banner=BANNER,
|
||||
is_hidden=True,
|
||||
)
|
||||
|
||||
|
||||
@ -25,11 +25,11 @@ class ExamplePlugin(CementPlugin):
|
||||
|
||||
def __init__(self):
|
||||
CementPlugin.__init__(self,
|
||||
label = 'example',
|
||||
version = VERSION,
|
||||
description = 'Example plugin for {{package}}',
|
||||
required_api = REQUIRED_CEMENT_API,
|
||||
version_banner=BANNER,
|
||||
label='example',
|
||||
version=VERSION,
|
||||
description='Example plugin for {{package}}',
|
||||
required_api=REQUIRED_CEMENT_API,
|
||||
banner=BANNER,
|
||||
)
|
||||
|
||||
# plugin configurations can be setup this way
|
||||
|
||||
@ -27,11 +27,11 @@ class {{plugin}}Plugin(CementPlugin):
|
||||
|
||||
def __init__(self):
|
||||
CementPlugin.__init__(self,
|
||||
label = '{{plugin}}',
|
||||
version = VERSION,
|
||||
description = '{{plugin}} plugin for {{project}}',
|
||||
required_api = REQUIRED_CEMENT_API,
|
||||
version_banner=BANNER
|
||||
label='{{plugin}}',
|
||||
version=VERSION,
|
||||
description='{{plugin}} plugin for {{project}}',
|
||||
required_api=REQUIRED_CEMENT_API,
|
||||
banner=BANNER
|
||||
)
|
||||
|
||||
#
|
||||
|
||||
@ -24,7 +24,7 @@ plugin_dir = ./var/lib/helloworld/plugins.d
|
||||
# show_plugin_load = true
|
||||
|
||||
# toggle debug output... can be true, false, yes, no, 1, 0
|
||||
debug = true
|
||||
debug = false
|
||||
|
||||
# toggle the log level... can be info, warn, error, fatal, debug
|
||||
log_level = warn
|
||||
@ -34,4 +34,4 @@ log_to_console = true
|
||||
|
||||
# add any config options you'd like here
|
||||
#
|
||||
# myoption = this is my option
|
||||
# myoption = this is my option
|
||||
@ -29,7 +29,7 @@ def main():
|
||||
# Warning: You shouldn't modify below this point unless you know what
|
||||
# you're doing.
|
||||
|
||||
lay_cement(default_config, version_banner=BANNER)
|
||||
lay_cement(config=default_config, banner=BANNER)
|
||||
|
||||
log = get_logger(__name__)
|
||||
log.debug("Cement Framework Initialized!")
|
||||
|
||||
@ -25,11 +25,11 @@ class ExamplePlugin(CementPlugin):
|
||||
|
||||
def __init__(self):
|
||||
CementPlugin.__init__(self,
|
||||
label = 'example',
|
||||
version = VERSION,
|
||||
description = 'Example plugin for helloworld',
|
||||
required_api = REQUIRED_CEMENT_API,
|
||||
version_banner=BANNER,
|
||||
label='example',
|
||||
version=VERSION,
|
||||
description='Example plugin for helloworld',
|
||||
required_api=REQUIRED_CEMENT_API,
|
||||
banner=BANNER,
|
||||
)
|
||||
|
||||
# plugin configurations can be setup this way
|
||||
|
||||
@ -21,11 +21,11 @@ class helloworldPlugin(CementPlugin):
|
||||
|
||||
def __init__(self):
|
||||
CementPlugin.__init__(self,
|
||||
label = 'helloworld',
|
||||
version = VERSION,
|
||||
description = 'Core plugin for helloworld',
|
||||
required_api = REQUIRED_CEMENT_API,
|
||||
version_banner = BANNER,
|
||||
label='helloworld',
|
||||
version=VERSION,
|
||||
description='Core plugin for helloworld',
|
||||
required_api=REQUIRED_CEMENT_API,
|
||||
banner=BANNER,
|
||||
is_hidden=True,
|
||||
)
|
||||
|
||||
|
||||
@ -27,11 +27,11 @@ class sayhiPlugin(CementPlugin):
|
||||
|
||||
def __init__(self):
|
||||
CementPlugin.__init__(self,
|
||||
label = 'sayhi',
|
||||
version = VERSION,
|
||||
description = 'sayhi plugin for helloworld',
|
||||
required_api = REQUIRED_CEMENT_API,
|
||||
version_banner=BANNER
|
||||
label='sayhi',
|
||||
version=VERSION,
|
||||
description='sayhi plugin for helloworld',
|
||||
required_api=REQUIRED_CEMENT_API,
|
||||
banner=BANNER
|
||||
)
|
||||
|
||||
#
|
||||
|
||||
52
setup.py
52
setup.py
@ -4,34 +4,42 @@ import sys, os
|
||||
version = '0.5.1'
|
||||
|
||||
LONG = """
|
||||
Cement is a CLI Application Framework for Python. It promotes code re-use by
|
||||
way of plugins and helper libraries that can be maintained internally, or
|
||||
shared with the community. The MVC and overall framework design is very much
|
||||
inspired by the TurboGears2 web framework.
|
||||
Cement is an advanced CLI Application Framework for Python. It promotes code
|
||||
re-use by way of plugins and helper libraries that can be shared between
|
||||
any application built on Cement. The MVC and overall framework design is
|
||||
very much inspired by the TurboGears2 web framework. Its goal is to introduce
|
||||
a standard, and feature-full platform for both simple and complex command line
|
||||
applications as well as support rapid development needs without sacrificing
|
||||
quality.
|
||||
|
||||
At a minimum, Cement easily sets up the following:
|
||||
|
||||
* Configuration file parsing [using ConfigObj]
|
||||
* Command line arguments and option parsing [using OptParse]
|
||||
* Logging [using Logger]
|
||||
* Plugin support [partially using setuptools]
|
||||
* Basic "hook" support
|
||||
* Full MVC support for advanced application design
|
||||
* Text output rendering with Genshi templates
|
||||
At a minimum, Cement configures the following features for every application:
|
||||
::
|
||||
* Multiple Configuration file parsing (default: /etc, ~/)
|
||||
* Command line argument and option parsing
|
||||
* Dual Console/File Logging Support
|
||||
* Full Internal and External (3rd Party) Plugin support
|
||||
* Basic "hook" support
|
||||
* Full MVC support for advanced application design
|
||||
* Text output rendering with Genshi templates
|
||||
* Json output rendering allows other programs to access your CLI-API
|
||||
|
||||
|
||||
These pieces are important for any command line application..
|
||||
Normally to accomplish what's listed above would require hundreds of lines of
|
||||
code before you even begin working on your application logic. With Cement, the
|
||||
above is configured with more or less a single command (via paste).
|
||||
The above provides any level developer with a solid, and fully functional
|
||||
cli application from the very start with more or less a single command via
|
||||
the paster utility. Cement brings an end to the 'hack it out, and [maybe]
|
||||
clean it up later' routine that we all find ourselves in under deadlines.
|
||||
|
||||
Cement is most generally used as a starting point from which to begin
|
||||
developing a command line type application. That said, applications using
|
||||
cement can also share plugins with either cement or other applications using
|
||||
cement.
|
||||
Any application can utilize existing plugins from the CementPlugins
|
||||
project, or from other 3rd party resources to extend functionality. The
|
||||
plugin system is designed to allow portability of re-usable code, and it
|
||||
is encouraged to contribute any plugins back to the project to extend the
|
||||
functionality of Cement.
|
||||
|
||||
The Cement CLI Application Framework for Python is Open Source and is
|
||||
distributed under the Python Software Foundation License.
|
||||
distributed under the Python Software Foundation License. When creating
|
||||
plugins specifically for re-use within the community, please be sure to
|
||||
follow the standard naming convention "HelloWorld Plugin for Cement" as an
|
||||
example. The actual module name should be 'cement.plugins.helloworld'.
|
||||
|
||||
|
||||
GETTING STARTED:
|
||||
|
||||
Loading…
Reference in New Issue
Block a user