def diff(content_old, content_new, filename, encoding_hint=None): output = "" LOG.debug("diffing {filename}: {len_before} B before, {len_after} B after".format( filename=filename, len_before=len(content_old), len_after=len(content_new), )) start = datetime.now() for line in unified_diff( content_old.splitlines(True), content_new.splitlines(True), fromfile=filename, tofile=_("<blockwart content>"), ): suffix = "" try: line = line.decode('UTF-8') except UnicodeDecodeError: if encoding_hint and encoding_hint.lower() != "utf-8": try: line = line.decode(encoding_hint) suffix += _(" (line encoded in {})").format(encoding_hint) except UnicodeDecodeError: line = line[0] suffix += _(" (line not encoded in UTF-8 or {})").format(encoding_hint) else: line = line[0] suffix += _(" (line not encoded in UTF-8)") line = line.rstrip("\n") if len(line) > DIFF_MAX_LINE_LENGTH: line = line[:DIFF_MAX_LINE_LENGTH] suffix += _(" (line truncated after {} characters)").format(DIFF_MAX_LINE_LENGTH) if line.startswith("+"): line = green(line) elif line.startswith("-"): line = red(line) output += line + suffix + "\n" duration = datetime.now() - start LOG.debug("diffing {file}: complete after {time}s".format( file=filename, time=duration.total_seconds(), )) return output
def get_result(self, interactive=False, interactive_default=True): if interactive is False and self.attributes['interactive'] is True: return self.STATUS_ACTION_SKIPPED if self.triggered and not self.has_been_triggered: LOG.debug(_("skipping {} because it wasn't triggered").format(self.id)) return self.STATUS_ACTION_SKIPPED if self.unless: unless_result = self.bundle.node.run( self.unless, may_fail=True, ) if unless_result.return_code == 0: LOG.debug(_("{node}:action:{name}: failed 'unless', not running").format( name=self.name, node=self.bundle.node.name, )) return self.STATUS_ACTION_SKIPPED if ( interactive and self.attributes['interactive'] is not False and not ask_interactively( wrap_question( self.id, self.attributes['command'], _("Run action {}?").format( bold(self.name), ), ), interactive_default, ) ): return self.STATUS_ACTION_SKIPPED try: self.run(interactive=interactive) return self.STATUS_ACTION_OK except ActionFailure: return self.STATUS_ACTION_FAILED
def content_processor_mako(item): from mako.template import Template template = Template( item._template_content, input_encoding='utf-8', output_encoding=item.attributes['encoding'], ) LOG.debug("{}:{}: rendering with Mako...".format(item.node.name, item.id)) start = datetime.now() try: content = template.render( item=item, bundle=item.bundle, node=item.node, repo=item.node.repo, **item.attributes['context'] ) except Exception as e: LOG.debug("".join(format_exception(*exc_info()))) if isinstance(e, NameError) and e.message == "Undefined": # Mako isn't very verbose here. Try to give a more useful # error message - even though we can't pinpoint the excat # location of the error. :/ e = _("Undefined variable (look for '${...}')") raise TemplateError(_( "Error while rendering template for {node}:{item}: {error}" ).format( error=e, item=item.id, node=item.node.name, )) duration = datetime.now() - start LOG.debug("{node}:{item}: rendered in {time}s".format( item=item.id, node=item.node.name, time=duration.total_seconds(), )) return content
def apply(self, interactive=False, interactive_default=True): self.node.repo.hooks.item_apply_start( self.node.repo, self.node, self, ) status_code = None status_before = None status_after = None start_time = datetime.now() if self.triggered and not self.has_been_triggered: LOG.debug(_("skipping {} because it wasn't triggered").format(self.id)) status_code = self.STATUS_SKIPPED if status_code is None: status_before = self.get_status() if self.unless and not status_before.correct: unless_result = self.node.run(self.unless, may_fail=True) if unless_result.return_code == 0: LOG.debug(_("'unless' for {} succeeded, not fixing").format(self.id)) status_code = self.STATUS_SKIPPED if status_code is None: if status_before.correct: status_code = self.STATUS_OK if status_code is None: if not interactive: self.fix(status_before) status_after = self.get_status() else: question = wrap_question( self.id, self.ask(status_before), _("Fix {}?").format(bold(self.id)), ) if ask_interactively(question, interactive_default): self.fix(status_before) status_after = self.get_status() else: status_code = self.STATUS_SKIPPED if status_code is None: if status_after.correct: status_code = self.STATUS_FIXED else: status_code = self.STATUS_FAILED self.node.repo.hooks.item_apply_end( self.node.repo, self.node, self, duration=datetime.now() - start_time, status_code=status_code, status_before=status_before, status_after=status_after, ) return status_code