Skip to content

Instantly share code, notes, and snippets.

@petri
Forked from joshbode/LICENSE.md
Created January 5, 2017 13:30
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save petri/008e63aa279e940cb364a36b5cc71988 to your computer and use it in GitHub Desktop.
Save petri/008e63aa279e940cb364a36b5cc71988 to your computer and use it in GitHub Desktop.
YAML Loader with include constructor (Python 3)
import yaml
import os.path
class LoaderMeta(type):
def __new__(metacls, __name__, __bases__, __dict__):
"""Add include constructer to class."""
# register the include constructor on the class
cls = super().__new__(metacls, __name__, __bases__, __dict__)
cls.add_constructor('!include', cls.construct_include)
return cls
class Loader(yaml.Loader, metaclass=LoaderMeta):
"""YAML Loader with `!include` constructor."""
def __init__(self, stream):
"""Initialise Loader."""
try:
self._root = os.path.split(stream.name)[0]
except AttributeError:
self._root = os.path.curdir
super().__init__(stream)
def construct_include(self, node):
"""Include file referenced at node."""
filename = os.path.abspath(os.path.join(
self._root, self.construct_scalar(node)
))
extension = os.path.splitext(filename)[1].lstrip('.')
with open(filename, 'r') as f:
if extension in ('yaml', 'yml'):
return yaml.load(f, Loader)
else:
return ''.join(f.readlines())
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment