60 lines
1.8 KiB
Python
60 lines
1.8 KiB
Python
from . import logging
|
|
import jinja2
|
|
import os
|
|
import pkg_resources
|
|
|
|
__all__ = ['Renderer']
|
|
|
|
|
|
LOG = logging.getLogger(__name__)
|
|
|
|
|
|
class Renderer:
|
|
def __init__(self, *, node_data, target_dir):
|
|
self.data = node_data
|
|
self.target_dir = target_dir
|
|
|
|
@property
|
|
def template_paths(self):
|
|
return ['common'] + self.data['current_node']['roles']
|
|
|
|
def render(self):
|
|
for template_dir in self.template_paths:
|
|
self.render_template_dir(template_dir)
|
|
|
|
|
|
def render_template_dir(self, template_dir):
|
|
source_root = pkg_resources.resource_filename(
|
|
'promenade', os.path.join('templates', template_dir))
|
|
LOG.debug('Searching for templates in: "%s"', source_root)
|
|
for root, _dirnames, filenames in os.walk(source_root,
|
|
followlinks=True):
|
|
for source_filename in filenames:
|
|
source_path = os.path.join(root, source_filename)
|
|
self.render_template_file(path=source_path,
|
|
root=source_root)
|
|
|
|
def render_template_file(self, *, path, root):
|
|
base_path = os.path.relpath(path, root)
|
|
target_path = os.path.join(self.target_dir, base_path)
|
|
|
|
_ensure_path(target_path)
|
|
|
|
LOG.debug('Templating "%s" into "%s"', path, target_path)
|
|
|
|
env = jinja2.Environment(undefined=jinja2.StrictUndefined)
|
|
|
|
with open(path) as f:
|
|
template = env.from_string(f.read())
|
|
rendered_data = template.render(**self.data)
|
|
|
|
with open(target_path, 'w') as f:
|
|
f.write(rendered_data)
|
|
|
|
LOG.info('Installed "%s"', os.path.join('/', base_path))
|
|
|
|
|
|
def _ensure_path(path):
|
|
base = os.path.dirname(path)
|
|
os.makedirs(base, mode=0o775, exist_ok=True)
|