diff piecrust/commands/builtin/publishing.py @ 758:6abb436fea5b

publish: Make publisher more powerful and better exposed on the command line. * Make the `chef publish` command have one sub-command per publish target. * Add custom argument parsing per publisher to have strong extra arguments available per publish target. * Make publish targets a first class citizen of the `PieCrust` app class.
author Ludovic Chabant <ludovic@chabant.com>
date Sat, 25 Jun 2016 17:03:29 -0700
parents 8f9c0bdb3724
children 71a755512eb8
line wrap: on
line diff
--- a/piecrust/commands/builtin/publishing.py	Sat Jun 25 17:01:08 2016 -0700
+++ b/piecrust/commands/builtin/publishing.py	Sat Jun 25 17:03:29 2016 -0700
@@ -1,6 +1,7 @@
 import logging
 import urllib.parse
 from piecrust.commands.base import ChefCommand
+from piecrust.pathutil import SiteNotFoundError
 from piecrust.publishing.publisher import Publisher, find_publisher_name
 
 
@@ -17,10 +18,6 @@
 
     def setupParser(self, parser, app):
         parser.add_argument(
-                '-l', '--list',
-                action='store_true',
-                help="List available publish targets for the current site.")
-        parser.add_argument(
                 '--log-publisher',
                 metavar='LOG_FILE',
                 help="Log the publisher's output to a given file.")
@@ -28,51 +25,39 @@
                 '--preview',
                 action='store_true',
                 help="Only preview what the publisher would do.")
-        parser.add_argument(
-                'target',
-                nargs='?',
-                default='default',
-                help="The publish target to use.")
 
-    def run(self, ctx):
-        if ctx.args.list:
-            pub_cfg = ctx.app.config.get('publish')
-            if not pub_cfg:
-                logger.info("No available publish targets.")
-                return
+        subparsers = parser.add_subparsers()
+        for pub in app.publishers:
+            p = subparsers.add_parser(
+                    pub.target,
+                    help="Publish using target '%s'." % pub.target)
+            pub.setupPublishParser(p, app)
+            p.set_defaults(sub_func=self._doPublish)
+            p.set_defaults(target=pub.target)
 
-            for name, cfg in pub_cfg.items():
-                if isinstance(cfg, dict):
-                    pub_type = cfg.get('type')
-                    if pub_type:
-                        desc = cfg.get('description')
-                        bake_first = cfg.get('bake', True)
-                        msg = '%s (%s)' % (name, pub_type)
-                        if not bake_first:
-                            msg += ' (no local baking)'
-                        if desc:
-                            msg += ': ' + desc
-                        logger.info(msg)
-                    else:
-                        logger.error(
-                                "%s (unknown type '%s')" % (name, pub_type))
-                elif isinstance(cfg, str):
-                    comps = urllib.parse.urlparse(str(cfg))
-                    pub_name = find_publisher_name(ctx.app, comps.scheme)
-                    if pub_name:
-                        logger.info("%s (%s)" % (name, pub_name))
-                    else:
-                        logger.error(
-                                "%s (unknown scheme '%s')" %
-                                (name, comps.scheme))
-                else:
-                    logger.error(
-                            "%s (incorrect configuration)" % name)
+        if not app.publishers:
+            parser.epilog = (
+                "No publishers have been defined. You can define publishers "
+                "through the `publish` configuration settings. "
+                "For more information see: "
+                "https://bolt80.com/piecrust/en/latest/docs/publishing/")
+
+    def checkedRun(self, ctx):
+        if ctx.app.root_dir is None:
+            raise SiteNotFoundError(theme=ctx.app.theme_site)
+
+        if not hasattr(ctx.args, 'sub_func'):
+            ctx.parser.parse_args(['publish', '--help'])
             return
+        ctx.args.sub_func(ctx)
 
+    def _doPublish(self, ctx):
         pub = Publisher(ctx.app)
         pub.run(
                 ctx.args.target,
                 preview=ctx.args.preview,
-                log_file=ctx.args.log_publisher)
+                extra_args=ctx.args,
+                log_file=ctx.args.log_publisher,
+                applied_config_variant=ctx.config_variant,
+                applied_config_values=ctx.config_values)