comparison piecrust/publishing/shell.py @ 621:8f9c0bdb3724

publish: Polish/refactor the publishing workflows. * Add a `--preview` option. * The `--list` option gives a nicer output, and prints warnings/errors for incorrect configuration. * Moved most of the `shell` code into a base class that's reusable. * Simplified the code to log publishing to a file. * Nicer output overall, with times.
author Ludovic Chabant <ludovic@chabant.com>
date Mon, 08 Feb 2016 20:44:26 -0800
parents a2d9ef307a08
children 42da89d8bd51
comparison
equal deleted inserted replaced
620:c2708f20a87b 621:8f9c0bdb3724
1 import sys
2 import shlex 1 import shlex
3 import logging 2 from piecrust.publishing.base import ShellCommandPublisherBase
4 import threading
5 import subprocess
6 from piecrust.publishing.base import Publisher
7 3
8 4
9 logger = logging.getLogger(__name__) 5 class ShellCommandPublisher(ShellCommandPublisherBase):
10
11
12 class ShellCommandPublisher(Publisher):
13 PUBLISHER_NAME = 'shell' 6 PUBLISHER_NAME = 'shell'
14 7
15 def __init__(self, app, target): 8 def _getCommandArgs(self, ctx):
16 super(ShellCommandPublisher, self).__init__(app, target)
17 self.is_using_custom_logging = True
18
19 def run(self, ctx):
20 target_cmd = self.getConfigValue('cmd') 9 target_cmd = self.getConfigValue('cmd')
21 if not target_cmd: 10 if not target_cmd:
22 raise Exception("No command specified for publish target: %s" % 11 raise Exception("No command specified for publish target: %s" %
23 self.target) 12 self.target)
24 args = shlex.split(target_cmd) 13 args = shlex.split(target_cmd)
14 return args
25 15
26 logger.debug(
27 "Running shell command: %s" % args)
28
29 proc = subprocess.Popen(
30 args, cwd=self.app.root_dir, bufsize=0,
31 stdout=subprocess.PIPE,
32 universal_newlines=False)
33
34 logger.debug("Running publishing monitor for PID %d" % proc.pid)
35 thread = _PublishThread(proc, ctx.custom_logging_file)
36 thread.start()
37 proc.wait()
38 thread.join()
39
40 if proc.returncode != 0:
41 logger.error(
42 "Publish process returned code %d" % proc.returncode)
43 else:
44 logger.debug("Publish process returned successfully.")
45
46 return proc.returncode == 0
47
48
49 class _PublishThread(threading.Thread):
50 def __init__(self, proc, log_fp):
51 super(_PublishThread, self).__init__(
52 name='publish_monitor', daemon=True)
53 self.proc = proc
54 self.log_fp = log_fp
55
56 def run(self):
57 for line in iter(self.proc.stdout.readline, b''):
58 line_str = line.decode('utf8')
59 sys.stdout.write(line_str)
60 sys.stdout.flush()
61 if self.log_fp:
62 self.log_fp.write(line_str)
63 self.log_fp.flush()
64
65 self.proc.communicate()
66 logger.debug("Publish monitor exiting.")
67