/usr/share/doc/python-cement-doc/html/_sources/dev/quickstart.txt is in python-cement-doc 2.10.0-1.
This file is owned by root:root, with mode 0o644.
The actual contents of the file can be viewed below.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 | Quick Start
===========
The following creates and runs a sample 'helloworld' application.
*helloworld.py*
.. code-block:: python
from cement.core.foundation import CementApp
with CementApp('helloworld') as app:
app.run()
print('Hello World')
The above is equivalent to (should you need more control over setup and
closing an application):
.. code-block:: python
from cement.core.foundation import CementApp
app = CementApp('helloworld')
app.setup()
app.run()
print('Hello World')
app.close()
Running the application looks like:
.. code-block:: text
$ python helloworld.py
Hello World
Oh, I can just here you saying, "Whoa whoa... hang on a minute. This is a joke
right, all you did was print 'Hello World' to STDOUT. What kind of framework
is this?". Well obviously this is just an introduction to show that the
creation of an application is dead simple. Lets take a look further:
.. code-block:: text
$ python helloworld.py --help
usage: helloworld.py [-h] [--debug] [--quiet]
optional arguments:
-h, --help show this help message and exit
--debug toggle debug output
--quiet suppress all output
Oh nice, ok... ArgParse is already setup with a few options I see. What else?
.. code-block:: text
$ python helloworld.py --debug
2014-04-15 12:28:24,705 (DEBUG) cement.core.foundation : laying cement for the 'helloworld' application
2014-04-15 12:28:24,705 (DEBUG) cement.core.hook : defining hook 'pre_setup'
2014-04-15 12:28:24,705 (DEBUG) cement.core.hook : defining hook 'post_setup'
2014-04-15 12:28:24,705 (DEBUG) cement.core.hook : defining hook 'pre_run'
2014-04-15 12:28:24,705 (DEBUG) cement.core.hook : defining hook 'post_run'
2014-04-15 12:28:24,706 (DEBUG) cement.core.hook : defining hook 'pre_argument_parsing'
2014-04-15 12:28:24,706 (DEBUG) cement.core.hook : defining hook 'post_argument_parsing'
2014-04-15 12:28:24,706 (DEBUG) cement.core.hook : defining hook 'pre_close'
2014-04-15 12:28:24,706 (DEBUG) cement.core.hook : defining hook 'post_close'
2014-04-15 12:28:24,706 (DEBUG) cement.core.hook : defining hook 'signal'
2014-04-15 12:28:24,706 (DEBUG) cement.core.hook : defining hook 'pre_render'
2014-04-15 12:28:24,706 (DEBUG) cement.core.hook : defining hook 'post_render'
2014-04-15 12:28:24,706 (DEBUG) cement.core.handler : defining handler type 'extension' (IExtension)
2014-04-15 12:28:24,706 (DEBUG) cement.core.handler : defining handler type 'log' (ILog)
2014-04-15 12:28:24,706 (DEBUG) cement.core.handler : defining handler type 'config' (IConfig)
2014-04-15 12:28:24,706 (DEBUG) cement.core.handler : defining handler type 'plugin' (IPlugin)
2014-04-15 12:28:24,706 (DEBUG) cement.core.handler : defining handler type 'output' (IOutput)
2014-04-15 12:28:24,706 (DEBUG) cement.core.handler : defining handler type 'argument' (IArgument)
2014-04-15 12:28:24,706 (DEBUG) cement.core.handler : defining handler type 'controller' (IController)
2014-04-15 12:28:24,706 (DEBUG) cement.core.handler : defining handler type 'cache' (ICache)
2014-04-15 12:28:24,706 (DEBUG) cement.core.handler : registering handler '<class 'cement.core.extension.CementExtensionHandler'>' into handlers['extension']['cement']
2014-04-15 12:28:24,706 (DEBUG) cement.core.foundation : now setting up the 'helloworld' application
2014-04-15 12:28:24,706 (DEBUG) cement.core.foundation : adding signal handler for signal 15
2014-04-15 12:28:24,712 (DEBUG) cement.core.foundation : adding signal handler for signal 2
2014-04-15 12:28:24,712 (DEBUG) cement.core.foundation : setting up helloworld.extension handler
2014-04-15 12:28:24,712 (DEBUG) cement.core.extension : loading the 'cement.ext.ext_dummy' framework extension
2014-04-15 12:28:24,712 (DEBUG) cement.core.handler : registering handler '<class 'cement.ext.ext_dummy.DummyOutputHandler'>' into handlers['output']['null']
2014-04-15 12:28:24,712 (DEBUG) cement.core.extension : loading the 'cement.ext.ext_plugin' framework extension
2014-04-15 12:28:24,713 (DEBUG) cement.core.handler : registering handler '<class 'cement.ext.ext_plugin.CementPluginHandler'>' into handlers['plugin']['cement']
2014-04-15 12:28:24,713 (DEBUG) cement.core.extension : loading the 'cement.ext.ext_configparser' framework extension
2014-04-15 12:28:24,713 (DEBUG) cement.core.handler : registering handler '<class 'cement.ext.ext_configparser.ConfigParserConfigHandler'>' into handlers['config']['configparser']
2014-04-15 12:28:24,713 (DEBUG) cement.core.extension : loading the 'cement.ext.ext_logging' framework extension
2014-04-15 12:28:24,713 (DEBUG) cement.core.handler : registering handler '<class 'cement.ext.ext_logging.LoggingLogHandler'>' into handlers['log']['logging']
2014-04-15 12:28:24,713 (DEBUG) cement.core.extension : loading the 'cement.ext.ext_argparse' framework extension
2014-04-15 12:28:24,714 (DEBUG) cement.core.handler : registering handler '<class 'cement.ext.ext_argparse.ArgParseArgumentHandler'>' into handlers['argument']['argparse']
2014-04-15 12:28:24,714 (DEBUG) cement.core.foundation : setting up helloworld.config handler
2014-04-15 12:28:24,714 (DEBUG) cement.ext.ext_configparser : config file '/etc/helloworld/helloworld.conf' does not exist, skipping...
2014-04-15 12:28:24,714 (DEBUG) cement.ext.ext_configparser : config file '/Users/derks/.helloworld/config' does not exist, skipping...
2014-04-15 12:28:24,715 (DEBUG) cement.core.foundation : no cache handler defined, skipping.
2014-04-15 12:28:24,715 (DEBUG) cement.core.foundation : setting up helloworld.log handler
2014-04-15 12:28:24,715 (DEBUG) cement.core.handler : merging config defaults from '<cement.ext.ext_logging.LoggingLogHandler object at 0x1015c4ed0>' into section 'log.logging'
2014-04-15 12:28:24,715 (DEBUG) helloworld:None : logging initialized for 'helloworld:None' using LoggingLogHandler
2014-04-15 12:28:24,715 (DEBUG) cement.core.foundation : setting up helloworld.plugin handler
2014-04-15 12:28:24,715 (DEBUG) cement.ext.ext_plugin : plugin config dir /Users/derks/Development/boss/tmp/helloworld/config/plugins.d does not exist.
2014-04-15 12:28:24,716 (DEBUG) cement.core.foundation : setting up helloworld.arg handler
2014-04-15 12:28:24,716 (DEBUG) cement.core.foundation : setting up helloworld.output handler
2014-04-15 12:28:24,716 (DEBUG) cement.core.foundation : setting up application controllers
Hello World
2014-04-15 12:28:24,716 (DEBUG) cement.core.foundation : closing the application
Damn son, WTF? Don't worry, we'll explain everything in the rest of the doc.
Getting Warmer
--------------
The following is a more advanced example that showcases some of the default
application features. Notice the creation of command line arguments, default
config creation, and logging.
*myapp.py*
.. code-block:: python
from cement.core.foundation import CementApp
from cement.core import hook
from cement.utils.misc import init_defaults
# define our default configuration options
defaults = init_defaults('myapp')
defaults['myapp']['debug'] = False
defaults['myapp']['some_param'] = 'some value'
# define any hook functions here
def my_cleanup_hook(app):
pass
# define the application class
class MyApp(CementApp):
class Meta:
label = 'myapp'
config_defaults = defaults
extensions = ['daemon', 'memcached', 'json', 'yaml']
hooks = [
('pre_close', my_cleanup_hook),
]
with MyApp() as app:
# add arguments to the parser
app.args.add_argument('-f', '--foo', action='store', metavar='STR',
help='the notorious foo option')
# log stuff
app.log.debug("About to run my myapp application!")
# run the application
app.run()
# continue with additional application logic
if app.pargs.foo:
app.log.info("Received option: foo => %s" % app.pargs.foo)
And execution:
.. code-block:: text
$ python myapp.py --help
usage: myapp.py (sub-commands ...) [options ...] {arguments ...}
optional arguments:
-h, --help show this help message and exit
--debug toggle debug output
--quiet suppress all output
-f STR, --foo STR the notorious foo option
$ python myapp.py --foo=bar
INFO: Received option: foo => bar
Diving Right In
---------------
This final example demonstrates the use of application controllers that
handle command dispatch and rapid development.
*myapp.py*
.. code-block:: python
from cement.core.foundation import CementApp
from cement.core.controller import CementBaseController, expose
class MyBaseController(CementBaseController):
class Meta:
label = 'base'
description = "My Application does amazing things!"
arguments = [
( ['-f', '--foo'],
dict(action='store', help='the notorious foo option') ),
( ['-C'],
dict(action='store_true', help='the big C option') ),
]
@expose(hide=True)
def default(self):
self.app.log.info('Inside MyBaseController.default()')
if self.app.pargs.foo:
print("Recieved option: foo => %s" % self.app.pargs.foo)
@expose(help="this command does relatively nothing useful")
def command1(self):
self.app.log.info("Inside MyBaseController.command1()")
@expose(aliases=['cmd2'], help="more of nothing")
def command2(self):
self.app.log.info("Inside MyBaseController.command2()")
class MySecondController(CementBaseController):
class Meta:
label = 'second'
stacked_on = 'base'
@expose(help='this is some command', aliases=['some-cmd'])
def second_cmd1(self):
self.app.log.info("Inside MySecondController.second_cmd1")
class MyApp(CementApp):
class Meta:
label = 'myapp'
base_controller = 'base'
handlers = [MyBaseController, MySecondController]
with MyApp() as app:
app.run()
As you can see, we're able to build out the core functionality of our app such
as arguments and sub-commands via controller classes.
Lets see what this looks like:
.. code-block:: text
$ python myapp.py --help
usage: myapp.py (sub-commands ...) [options ...] {arguments ...}
My Application does amazing things!
commands:
command1
this command does relatively nothing useful
command2 (aliases: cmd2)
more of nothing
second-cmd1 (aliases: some-cmd)
this is some command
optional arguments:
-h, --help show this help message and exit
--debug toggle debug output
--quiet suppress all output
-f FOO, --foo FOO the notorious foo option
-C the big C option
$ python myapp.py
INFO: Inside MyBaseController.default()
$ python myapp.py command1
INFO: Inside MyBaseController.command1()
$ python myapp.py command2
INFO: Inside MyBaseController.command2()
$ python myapp.py second-cmd1
INFO: Inside MySecondController.second_cmd1()
|