def runtest(self): fs = mock_fs() # Website config. config = { 'site': { 'default_format': 'none', 'default_page_layout': 'none', 'default_post_layout': 'none'} } test_config = self.spec.get('config') if test_config is not None: merge_dicts(config, test_config) fs.withConfig(config) # Input file-system. input_files = self.spec.get('in') if input_files is not None: _add_mock_files(fs, '/kitchen', input_files) # Output file-system. expected_output_files = self.spec.get('out') expected_partial_files = self.spec.get('outfiles') # Bake! from piecrust.baking.baker import Baker with mock_fs_scope(fs): out_dir = fs.path('kitchen/_counter') app = fs.getApp() baker = Baker(app, out_dir) baker.bake() if expected_output_files: actual = fs.getStructure('kitchen/_counter') error = _compare_dicts(expected_output_files, actual) if error: raise ExpectedBakeOutputError(error) if expected_partial_files: keys = list(sorted(expected_partial_files.keys())) for key in keys: try: actual = fs.getFileEntry('kitchen/_counter/' + key.lstrip('/')) except Exception as e: raise ExpectedBakeOutputError([ "Can't access output file %s: %s" % (key, e)]) expected = expected_partial_files[key] # HACK because for some reason PyYAML adds a new line for those # and I have no idea why. actual = actual.rstrip('\n') expected = expected.rstrip('\n') cmpres = _compare_str(expected, actual, key) if cmpres: raise ExpectedBakeOutputError(cmpres)
def runtest(self): fs = self._prepareMockFs() from piecrust.baking.baker import Baker with mock_fs_scope(fs, keep=self.mock_debug): out_dir = fs.path('kitchen/_counter') app = fs.getApp(theme_site=self.is_theme_site) values = self.spec.get('config_values') if values is not None: values = list(values.items()) variants = self.spec.get('config_variants') apply_variants_and_values(app, variants, values) appfactory = PieCrustFactory(app.root_dir, theme_site=self.is_theme_site, config_variants=variants, config_values=values) baker = Baker(appfactory, app, out_dir) records = baker.bake() if not records.success: errors = [] for r in records.records: for e in r.getEntries(): errors += e.getAllErrors() raise BakeError(errors) check_expected_outputs(self.spec, fs, UnexpectedBakeOutputError)
def runtest(self): fs = self._prepareMockFs() from piecrust.baking.baker import Baker with mock_fs_scope(fs): out_dir = fs.path('kitchen/_counter') app = fs.getApp() variant = self.spec.get('config_variant') values = self.spec.get('config_values') if values is not None: values = list(values.items()) apply_variant_and_values(app, variant, values) baker = Baker(app, out_dir, applied_config_variant=variant, applied_config_values=values) record = baker.bake() if not record.success: errors = [] for e in record.entries: errors += e.getAllErrors() raise BakeError(errors) check_expected_outputs(self.spec, fs, ExpectedBakeOutputError)
def test_removed(): fs = (mock_fs() .withPage('pages/foo.md', {'layout': 'none', 'format': 'none'}, 'a foo page') .withPage('pages/_index.md', {'layout': 'none', 'format': 'none'}, "something")) with mock_fs_scope(fs): out_dir = fs.path('kitchen/_counter') app = fs.getApp() baker = Baker(app, out_dir) baker.bake() structure = fs.getStructure('kitchen/_counter') assert structure == { 'foo.html': 'a foo page', 'index.html': 'something'} os.remove(fs.path('kitchen/pages/foo.md')) app = fs.getApp() baker = Baker(app, out_dir) baker.bake() structure = fs.getStructure('kitchen/_counter') assert structure == { 'index.html': 'something'}
def test_record_version_change(): fs = (mock_fs() .withConfig() .withPage('pages/foo.md', {'layout': 'none', 'format': 'none'}, 'a foo page')) with mock_fs_scope(fs): out_dir = fs.path('kitchen/_counter') app = fs.getApp() baker = Baker(app, out_dir) baker.bake() mtime = os.path.getmtime(fs.path('kitchen/_counter/foo.html')) time.sleep(1) app = fs.getApp() baker = Baker(app, out_dir) baker.bake() assert mtime == os.path.getmtime(fs.path('kitchen/_counter/foo.html')) BakeRecord.RECORD_VERSION += 1 try: app = fs.getApp() baker = Baker(app, out_dir) baker.bake() assert mtime < os.path.getmtime(fs.path('kitchen/_counter/foo.html')) finally: BakeRecord.RECORD_VERSION -= 1
def _bakeSources(self, ctx, out_dir): if ctx.args.workers > 0: ctx.app.config.set('baker/workers', ctx.args.workers) if ctx.args.batch_size > 0: ctx.app.config.set('baker/batch_size', ctx.args.batch_size) baker = Baker( ctx.app, out_dir, force=ctx.args.force, applied_config_variant=ctx.config_variant, applied_config_values=ctx.config_values) record = baker.bake() _merge_timers(record.timers, ctx.timers) return record.success
def _bakeSources(self, ctx, out_dir): if ctx.args.workers > 0: ctx.app.config.set('baker/workers', ctx.args.workers) if ctx.args.batch_size > 0: ctx.app.config.set('baker/batch_size', ctx.args.batch_size) baker = Baker(ctx.app, out_dir, force=ctx.args.force, applied_config_variant=ctx.config_variant, applied_config_values=ctx.config_values) record = baker.bake() _merge_timers(record.timers, ctx.timers) return record.success
def _doRunPipelines(self, only_for_source): from piecrust.baking.baker import Baker allowed_sources = None if only_for_source: allowed_sources = [only_for_source.name] baker = Baker( self.appfactory, self._app, self.out_dir, allowed_pipelines=['asset'], allowed_sources=allowed_sources, rotate_bake_records=False, keep_unused_records=(allowed_sources is not None)) records = baker.bake() self._onPipelinesRun(records)
def _doRunPipelines(self, only_for_source): from piecrust.baking.baker import Baker allowed_sources = None if only_for_source: allowed_sources = [only_for_source.name] baker = Baker(self.appfactory, self._app, self.out_dir, allowed_pipelines=['asset'], allowed_sources=allowed_sources, rotate_bake_records=False, keep_unused_records=(allowed_sources is not None)) records = baker.bake() self._onPipelinesRun(records)
def runtest(self): fs = self._prepareMockFs() # Output file-system. expected_output_files = self.spec.get('out') expected_partial_files = self.spec.get('outfiles') # Bake! from piecrust.baking.baker import Baker with mock_fs_scope(fs): out_dir = fs.path('kitchen/_counter') app = fs.getApp() baker = Baker(app, out_dir) record = baker.bake() if not record.success: errors = [] for e in record.entries: errors += e.getAllErrors() raise BakeError(errors) if expected_output_files: actual = fs.getStructure('kitchen/_counter') error = _compare_dicts(expected_output_files, actual) if error: raise ExpectedBakeOutputError(error) if expected_partial_files: keys = list(sorted(expected_partial_files.keys())) for key in keys: try: actual = fs.getFileEntry('kitchen/_counter/' + key.lstrip('/')) except Exception as e: raise ExpectedBakeOutputError([ "Can't access output file %s: %s" % (key, e)]) expected = expected_partial_files[key] # HACK because for some reason PyYAML adds a new line for those # and I have no idea why. actual = actual.rstrip('\n') expected = expected.rstrip('\n') cmpres = _compare_str(expected, actual, key) if cmpres: raise ExpectedBakeOutputError(cmpres)
def _doBake(self, ctx, out_dir): from piecrust.baking.baker import Baker if ctx.args.workers > 0: ctx.app.config.set('baker/workers', ctx.args.workers) if ctx.args.batch_size > 0: ctx.app.config.set('baker/batch_size', ctx.args.batch_size) allowed_pipelines = None forbidden_pipelines = None if ctx.args.html_only: forbidden_pipelines = ['asset'] elif ctx.args.assets_only: allowed_pipelines = ['asset'] elif ctx.args.pipelines: if allowed_pipelines or forbidden_pipelines: raise Exception( "Can't specify `--html-only` or `--assets-only` with " "`--pipelines`.") allowed_pipelines = [] forbidden_pipelines = [] for p in ctx.args.pipelines: if p[0] == '-': forbidden_pipelines.append(p) else: allowed_pipelines.append(p) if not allowed_pipelines: allowed_pipelines = None if not forbidden_pipelines: forbidden_pipelines = None baker = Baker(ctx.appfactory, ctx.app, out_dir, force=ctx.args.force, allowed_sources=ctx.args.sources, allowed_pipelines=allowed_pipelines, forbidden_pipelines=forbidden_pipelines) records = baker.bake() return records
def test_record_version_change(): fs = (mock_fs() .withPage('pages/foo.md', {'layout': 'none', 'format': 'none'}, 'a foo page')) with mock_fs_scope(fs): out_dir = fs.path('kitchen/_counter') app = fs.getApp() baker = Baker(app, out_dir) baker.bake() mtime = os.path.getmtime(fs.path('kitchen/_counter/foo.html')) time.sleep(1) app = fs.getApp() baker = Baker(app, out_dir) baker.bake() assert mtime == os.path.getmtime(fs.path('kitchen/_counter/foo.html')) BakeRecord.RECORD_VERSION += 1 try: app = fs.getApp() baker = Baker(app, out_dir) baker.bake() assert mtime < os.path.getmtime(fs.path('kitchen/_counter/foo.html')) finally: BakeRecord.RECORD_VERSION -= 1
def _bakeSources(self, ctx, out_dir): baker = Baker(ctx.app, out_dir, force=ctx.args.force) record = baker.bake() return record.success
def _bakeSources(self, ctx, out_dir): baker = Baker( ctx.app, out_dir, force=ctx.args.force) record = baker.bake() return record.success
def run(self, target, force=False, preview=False, extra_args=None, log_file=None, log_debug_info=False, append_log_file=False): start_time = time.perf_counter() # Get publisher for this target. pub = self.app.getPublisher(target) if pub is None: raise InvalidPublishTargetError("No such publish target: %s" % target) # Will we need to bake first? bake_first = pub.config.get('bake', True) # Setup logging stuff. hdlr = None root_logger = logging.getLogger() if log_file and not preview: logger.debug("Adding file handler for: %s" % log_file) mode = 'w' if append_log_file: mode = 'a' hdlr = logging.FileHandler(log_file, mode=mode, encoding='utf8') root_logger.addHandler(hdlr) if log_debug_info: _log_debug_info(target, force, preview, extra_args) if not preview: logger.info("Deploying to %s" % target) else: logger.info("Previewing deployment to %s" % target) # Bake first is necessary. records = None was_baked = False bake_out_dir = os.path.join(self.app.root_dir, '_pub', target) if bake_first: if not preview: bake_start_time = time.perf_counter() logger.debug("Baking first to: %s" % bake_out_dir) from piecrust.baking.baker import Baker baker = Baker(self.appfactory, self.app, bake_out_dir, force=force) records = baker.bake() was_baked = True if not records.success: raise Exception( "Error during baking, aborting publishing.") logger.info(format_timed(bake_start_time, "Baked website.")) else: logger.info("Would bake to: %s" % bake_out_dir) # Publish! logger.debug("Running publish target '%s' with publisher: %s" % (target, pub.PUBLISHER_NAME)) pub_start_time = time.perf_counter() success = False ctx = PublishingContext() ctx.bake_out_dir = bake_out_dir ctx.bake_records = records ctx.was_baked = was_baked ctx.preview = preview ctx.args = extra_args try: success = pub.run(ctx) except Exception as ex: raise PublishingError("Error publishing to target: %s" % target) from ex finally: if hdlr: root_logger.removeHandler(hdlr) hdlr.close() logger.info( format_timed(pub_start_time, "Ran publisher %s" % pub.PUBLISHER_NAME)) if success: logger.info(format_timed(start_time, 'Deployed to %s' % target)) return 0 else: logger.error( format_timed(start_time, 'Failed to deploy to %s' % target)) return 1
def run(self, target, force=False, preview=False, extra_args=None, log_file=None, log_debug_info=False, append_log_file=False): start_time = time.perf_counter() # Get publisher for this target. pub = self.app.getPublisher(target) if pub is None: raise InvalidPublishTargetError( "No such publish target: %s" % target) # Will we need to bake first? bake_first = pub.config.get('bake', True) # Setup logging stuff. hdlr = None root_logger = logging.getLogger() if log_file and not preview: logger.debug("Adding file handler for: %s" % log_file) mode = 'w' if append_log_file: mode = 'a' hdlr = logging.FileHandler(log_file, mode=mode, encoding='utf8') root_logger.addHandler(hdlr) if log_debug_info: _log_debug_info(target, force, preview, extra_args) if not preview: logger.info("Deploying to %s" % target) else: logger.info("Previewing deployment to %s" % target) # Bake first is necessary. records = None was_baked = False bake_out_dir = os.path.join(self.app.root_dir, '_pub', target) if bake_first: if not preview: bake_start_time = time.perf_counter() logger.debug("Baking first to: %s" % bake_out_dir) from piecrust.baking.baker import Baker baker = Baker( self.appfactory, self.app, bake_out_dir, force=force) records = baker.bake() was_baked = True if not records.success: raise Exception( "Error during baking, aborting publishing.") logger.info(format_timed(bake_start_time, "Baked website.")) else: logger.info("Would bake to: %s" % bake_out_dir) # Publish! logger.debug( "Running publish target '%s' with publisher: %s" % (target, pub.PUBLISHER_NAME)) pub_start_time = time.perf_counter() success = False ctx = PublishingContext() ctx.bake_out_dir = bake_out_dir ctx.bake_records = records ctx.was_baked = was_baked ctx.preview = preview ctx.args = extra_args try: success = pub.run(ctx) except Exception as ex: raise PublishingError( "Error publishing to target: %s" % target) from ex finally: if hdlr: root_logger.removeHandler(hdlr) hdlr.close() logger.info(format_timed( pub_start_time, "Ran publisher %s" % pub.PUBLISHER_NAME)) if success: logger.info(format_timed(start_time, 'Deployed to %s' % target)) return 0 else: logger.error(format_timed(start_time, 'Failed to deploy to %s' % target)) return 1
def run(self, target, force=False, preview=False, extra_args=None, log_file=None, applied_config_variant=None, applied_config_values=None): start_time = time.perf_counter() # Get publisher for this target. pub = self.app.getPublisher(target) if pub is None: raise InvalidPublishTargetError( "No such publish target: %s" % target) # Will we need to bake first? bake_first = True if not pub.has_url_config: bake_first = pub.getConfigValue('bake', True) # Setup logging stuff. hdlr = None root_logger = logging.getLogger() if log_file and not preview: logger.debug("Adding file handler for: %s" % log_file) hdlr = logging.FileHandler(log_file, mode='w', encoding='utf8') root_logger.addHandler(hdlr) if not preview: logger.info("Deploying to %s" % target) else: logger.info("Previewing deployment to %s" % target) # Bake first is necessary. rec1 = None rec2 = None was_baked = False bake_out_dir = os.path.join(self.app.root_dir, '_pub', target) if bake_first: if not preview: bake_start_time = time.perf_counter() logger.debug("Baking first to: %s" % bake_out_dir) from piecrust.baking.baker import Baker baker = Baker( self.app, bake_out_dir, applied_config_variant=applied_config_variant, applied_config_values=applied_config_values) rec1 = baker.bake() from piecrust.processing.pipeline import ProcessorPipeline proc = ProcessorPipeline( self.app, bake_out_dir, applied_config_variant=applied_config_variant, applied_config_values=applied_config_values) rec2 = proc.run() was_baked = True if not rec1.success or not rec2.success: raise Exception( "Error during baking, aborting publishing.") logger.info(format_timed(bake_start_time, "Baked website.")) else: logger.info("Would bake to: %s" % bake_out_dir) # Publish! logger.debug( "Running publish target '%s' with publisher: %s" % (target, pub.PUBLISHER_NAME)) pub_start_time = time.perf_counter() ctx = PublishingContext() ctx.bake_out_dir = bake_out_dir ctx.bake_record = rec1 ctx.processing_record = rec2 ctx.was_baked = was_baked ctx.preview = preview ctx.args = extra_args try: pub.run(ctx) except Exception as ex: raise PublishingError( "Error publishing to target: %s" % target) from ex finally: if hdlr: root_logger.removeHandler(hdlr) hdlr.close() logger.info(format_timed( pub_start_time, "Ran publisher %s" % pub.PUBLISHER_NAME)) logger.info(format_timed(start_time, 'Deployed to %s' % target))