From eec16a112e0fdab8eb317b4c802a7660c31559a5 Mon Sep 17 00:00:00 2001 From: Lakshmi Vyasarajan Date: Thu, 8 Dec 2011 16:11:30 +0530 Subject: [PATCH] Issue #121: Added simple_copy feature for deploying unprocessable files --- CHANGELOG.rst | 6 ++ README.rst | 2 +- hyde/generator.py | 16 ++-- hyde/model.py | 1 + hyde/site.py | 5 +- hyde/tests/test_simple_copy.py | 139 +++++++++++++++++++++++++++++++++ hyde/tests/test_site.py | 61 +-------------- hyde/version.py | 2 +- 8 files changed, 161 insertions(+), 71 deletions(-) create mode 100644 hyde/tests/test_simple_copy.py diff --git a/CHANGELOG.rst b/CHANGELOG.rst index 67c3a50..1bdf1b4 100644 --- a/CHANGELOG.rst +++ b/CHANGELOG.rst @@ -1,3 +1,9 @@ +Version 0.8.5a8 +============================================================ + +* Added `simple_copy` feature to account for unprocessable files that + are nonetheless required to be deployed (Issue #121) + Version 0.8.5a7 ============================================================ * Bug Fix: Relative path was used in the server as the sitepath (Issue #119) diff --git a/README.rst b/README.rst index 589cf7a..b0d5488 100644 --- a/README.rst +++ b/README.rst @@ -1,4 +1,4 @@ -Version 0.8.5a7 +Version 0.8.5a8 A brand new **hyde** ==================== diff --git a/hyde/generator.py b/hyde/generator.py index 6649b9e..a87af6f 100644 --- a/hyde/generator.py +++ b/hyde/generator.py @@ -314,7 +314,13 @@ class Generator(object): return logger.debug("Processing [%s]", resource) with self.context_for_resource(resource) as context: - if resource.source_file.is_text: + target = File(self.site.config.deploy_root_path.child( + resource.relative_deploy_path)) + target.parent.make() + if resource.simple_copy: + logger.debug("Simply Copying [%s]", resource) + resource.source_file.copy_to(target) + elif resource.source_file.is_text: self.update_deps(resource) if resource.uses_template: logger.debug("Rendering [%s]", resource) @@ -331,16 +337,10 @@ class Generator(object): text = self.events.text_resource_complete( resource, text) or text - target = File(self.site.config.deploy_root_path.child( - resource.relative_deploy_path)) - target.parent.make() target.write(text) copymode(resource.source_file.path, target.path) else: logger.debug("Copying binary file [%s]", resource) self.events.begin_binary_resource(resource) - target = File(self.site.config.deploy_root_path.child( - resource.relative_deploy_path)) - target.parent.make() resource.source_file.copy_to(target) - self.events.binary_resource_complete(resource) + self.events.binary_resource_complete(resource) \ No newline at end of file diff --git a/hyde/model.py b/hyde/model.py index bef9a34..6185c45 100644 --- a/hyde/model.py +++ b/hyde/model.py @@ -142,6 +142,7 @@ class Config(Expando): def __init__(self, sitepath, config_file=None, config_dict=None): self.default_config = dict( mode='production', + simple_copy = [], content_root='content', deploy_root='deploy', media_root='media', diff --git a/hyde/site.py b/hyde/site.py index c741cbf..69feb8e 100644 --- a/hyde/site.py +++ b/hyde/site.py @@ -67,6 +67,7 @@ class Resource(Processable): self.node = node self.site = node.site self._relative_deploy_path = None + self.simple_copy = False @property def relative_path(self): @@ -333,7 +334,9 @@ class RootNode(Node): resource = node.add_child_resource(afile) self.resource_map[unicode(afile)] = resource relative_path = resource.relative_path - resource.simple_copy = any(fnmatch.fnmatch(relative_path, pattern) for pattern in self.site.config.simple_copy) + resource.simple_copy = any(fnmatch.fnmatch(relative_path, pattern) + for pattern + in self.site.config.simple_copy) logger.debug("Added resource [%s] to [%s]" % (resource.relative_path, self.source_folder)) diff --git a/hyde/tests/test_simple_copy.py b/hyde/tests/test_simple_copy.py new file mode 100644 index 0000000..cb34e82 --- /dev/null +++ b/hyde/tests/test_simple_copy.py @@ -0,0 +1,139 @@ +# -*- coding: utf-8 -*- +""" +Tests the simple copy feature. + +In order to mark some files to simply be copied to the +destination without any processing what so ever add this +to the config (site.yaml for example): +simple_copy: + - media/css/*.css + - media/js/*.js + - **/*.js + +Matching is done with `fnmatch` module. So any `glob` that fnmatch +can process is a valid pattern. + +Use nose +`$ pip install nose` +`$ nosetests` +""" +import yaml +from urllib import quote + +from hyde.fs import File, Folder +from hyde.model import Config, Expando +from hyde.site import Node, RootNode, Site +from hyde.generator import Generator + +from nose.tools import raises, with_setup, nottest + +TEST_SITE_ROOT = File(__file__).parent.child_folder('sites/test_jinja') + +class TestSimpleCopy(object): + @classmethod + def setup_class(cls): + cls.SITE_PATH = File(__file__).parent.child_folder('sites/test_jinja_with_config') + cls.SITE_PATH.make() + TEST_SITE_ROOT.copy_contents_to(cls.SITE_PATH) + + @classmethod + def teardown_class(cls): + cls.SITE_PATH.delete() + + @nottest + def setup_config(self, passthru): + self.config_file = File(self.SITE_PATH.child('site.yaml')) + with open(self.config_file.path) as config: + conf = yaml.load(config) + conf['simple_copy'] = passthru + self.config = Config(sitepath=self.SITE_PATH, config_dict=conf) + + def test_simple_copy_basic(self): + self.setup_config([ + 'about.html' + ]) + s = Site(self.SITE_PATH, config=self.config) + s.load() + res = s.content.resource_from_relative_path('about.html') + assert res + assert res.simple_copy + + def test_simple_copy_directory(self): + self.setup_config([ + '**/*.html' + ]) + s = Site(self.SITE_PATH, config=self.config) + s.load() + res = s.content.resource_from_relative_path('about.html') + assert res + assert not res.simple_copy + res = s.content.resource_from_relative_path('blog/2010/december/merry-christmas.html') + assert res + assert res.simple_copy + + def test_simple_copy_multiple(self): + self.setup_config([ + '**/*.html', + 'media/css/*.css' + ]) + s = Site(self.SITE_PATH, config=self.config) + s.load() + res = s.content.resource_from_relative_path('about.html') + assert res + assert not res.simple_copy + res = s.content.resource_from_relative_path('blog/2010/december/merry-christmas.html') + assert res + assert res.simple_copy + res = s.content.resource_from_relative_path('media/css/site.css') + assert res + assert res.simple_copy + + def test_generator(self): + self.setup_config([ + '**/*.html', + 'media/css/*.css' + ]) + s = Site(self.SITE_PATH, self.config) + g = Generator(s) + g.generate_all() + source = s.content.resource_from_relative_path('blog/2010/december/merry-christmas.html') + target = File(s.config.deploy_root_path.child(source.relative_deploy_path)) + left = source.source_file.read_all() + right = target.read_all() + assert left == right + + def test_plugins(self): + + text = """ +--- +title: Hey +author: Me +twitter: @me +--- +{%% extends "base.html" %%} + +{%% block main %%} + Hi! + + I am a test template to make sure jinja2 generation works well with hyde. + {{resource.meta.title}} + {{resource.meta.author}} + {{resource.meta.twitter}} +{%% endblock %%} +""" + index = File(self.SITE_PATH.child('content/blog/index.html')) + index.write(text) + self.setup_config([ + '**/*.html', + 'media/css/*.css' + ]) + conf = {'plugins': ['hyde.ext.plugins.meta.MetaPlugin']} + conf.update(self.config.to_dict()) + s = Site(self.SITE_PATH, Config(sitepath=self.SITE_PATH, config_dict=conf)) + g = Generator(s) + g.generate_all() + source = s.content.resource_from_relative_path('blog/index.html') + target = File(s.config.deploy_root_path.child(source.relative_deploy_path)) + left = source.source_file.read_all() + right = target.read_all() + assert left == right \ No newline at end of file diff --git a/hyde/tests/test_site.py b/hyde/tests/test_site.py index 9d5e771..9c32a30 100644 --- a/hyde/tests/test_site.py +++ b/hyde/tests/test_site.py @@ -276,63 +276,4 @@ class TestSiteWithConfig(object): blog_node = s.content.node_from_relative_path('blog') assert not blog_node git_node = s.content.node_from_relative_path('.git') - assert not git_node - -class TestSimpleCopy(object): - @classmethod - def setup_class(cls): - cls.SITE_PATH = File(__file__).parent.child_folder('sites/test_jinja_with_config') - cls.SITE_PATH.make() - TEST_SITE_ROOT.copy_contents_to(cls.SITE_PATH) - - @classmethod - def teardown_class(cls): - cls.SITE_PATH.delete() - - @nottest - def setup_config(self, passthru): - self.config_file = File(self.SITE_PATH.child('site.yaml')) - with open(self.config_file.path) as config: - conf = yaml.load(config) - conf['simple_copy'] = passthru - self.config = Config(sitepath=self.SITE_PATH, config_dict=conf) - - def test_simple_copy_basic(self): - self.setup_config([ - 'about.html' - ]) - s = Site(self.SITE_PATH, config=self.config) - s.load() - res = s.content.resource_from_relative_path('about.html') - assert res - assert res.simple_copy - - def test_simple_copy_directory(self): - self.setup_config([ - '**/*.html' - ]) - s = Site(self.SITE_PATH, config=self.config) - s.load() - res = s.content.resource_from_relative_path('about.html') - assert res - assert not res.simple_copy - res = s.content.resource_from_relative_path('blog/2010/december/merry-christmas.html') - assert res - assert res.simple_copy - - def test_simple_copy_multiple(self): - self.setup_config([ - '**/*.html', - 'media/css/*.css' - ]) - s = Site(self.SITE_PATH, config=self.config) - s.load() - res = s.content.resource_from_relative_path('about.html') - assert res - assert not res.simple_copy - res = s.content.resource_from_relative_path('blog/2010/december/merry-christmas.html') - assert res - assert res.simple_copy - res = s.content.resource_from_relative_path('media/css/site.css') - assert res - assert res.simple_copy + assert not git_node \ No newline at end of file diff --git a/hyde/version.py b/hyde/version.py index 2ad7676..80a6dac 100644 --- a/hyde/version.py +++ b/hyde/version.py @@ -3,4 +3,4 @@ Handles hyde version TODO: Use fabric like versioning scheme """ -__version__ = '0.8.5a7' +__version__ = '0.8.5a8'