Mercurial > piecrust2
diff piecrust/commands/base.py @ 3:f485ba500df3
Gigantic change to basically make PieCrust 2 vaguely functional.
- Serving works, with debug window.
- Baking works, multi-threading, with dependency handling.
- Various things not implemented yet.
author | Ludovic Chabant <ludovic@chabant.com> |
---|---|
date | Sun, 10 Aug 2014 23:43:16 -0700 |
parents | aaa8fb7c8918 |
children | c8c522dacfea |
line wrap: on
line diff
--- a/piecrust/commands/base.py Wed Dec 25 22:16:46 2013 -0800 +++ b/piecrust/commands/base.py Sun Aug 10 23:43:16 2014 -0700 @@ -1,4 +1,5 @@ import logging +import functools from piecrust.pathutil import SiteNotFoundError @@ -9,6 +10,7 @@ def __init__(self, app, args): self.app = app self.args = args + self.result = 0 class ChefCommand(object): @@ -17,14 +19,71 @@ self.description = '__unknown__' self.requires_website = True - def setupParser(self, parser): + def setupParser(self, parser, app): raise NotImplementedError() def run(self, ctx): raise NotImplementedError() def _runFromChef(self, app, res): - if app.root is None and self.requires_website: + if app.root_dir is None and self.requires_website: raise SiteNotFoundError() - self.run(CommandContext(app, res)) + ctx = CommandContext(app, res) + self.run(ctx) + return ctx.result + + +class ExtendableChefCommand(ChefCommand): + def __init__(self): + super(ExtendableChefCommand, self).__init__() + self._extensions = None + + def setupParser(self, parser, app): + self._loadExtensions(app) + subparsers = parser.add_subparsers() + for e in self._extensions: + p = subparsers.add_parser(e.name, help=e.description) + e.setupParser(p, app) + p.set_defaults(func=e._runFromChef) + + def _loadExtensions(self, app): + if self._extensions is not None: + return + self._extensions = [] + for e in app.plugin_loader.getCommandExtensions(): + if e.command_name == self.name and e.supports(app): + self._extensions.append(e) + +class ChefCommandExtension(ChefCommand): + def __init__(self): + super(ChefCommandExtension, self).__init__() + self.command_name = '__unknown__' + + def supports(self, app): + return True + + +class _WrappedCommand(ChefCommand): + def __init__(self, func, name, description): + super(_WrappedCommand, self).__init__() + self.func = func + self.name = name + self.description = description + + def run(self, ctx): + self.func(ctx) + + +def simple_command(f, name, description=None): + @functools.wraps(f) + def wrapper(*args, **kwargs): + return f(*args, **kwargs) + cmd = _WrappedCommand(f, name, description) + f.__command_class__ = cmd + return wrapper + + +def get_func_command(f): + return getattr(f, '__command_class__') +