예제 #1
0
def construct_env_tag(loader: yaml.Loader, node: yaml.Node) -> Any:
    """Assign value of ENV variable referenced at node."""
    default = None
    if isinstance(node, yaml.nodes.ScalarNode):
        vars = [loader.construct_scalar(node)]
    elif isinstance(node, yaml.nodes.SequenceNode):
        child_nodes = node.value
        if len(child_nodes) > 1:
            # default is resolved using YAML's (implicit) types.
            default = loader.construct_object(child_nodes[-1])
            child_nodes = child_nodes[:-1]
        # Env Vars are resolved as string values, ignoring (implicit) types.
        vars = [loader.construct_scalar(child) for child in child_nodes]
    else:
        raise yaml.constructor.ConstructorError(
            None, None,
            f'expected a scalar or sequence node, but found {node.id}',
            node.start_mark)

    for var in vars:
        if var in os.environ:
            value = os.environ[var]
            # Resolve value to Python type using YAML's implicit resolvers
            tag = loader.resolve(yaml.nodes.ScalarNode, value, (True, False))
            return loader.construct_object(yaml.nodes.ScalarNode(tag, value))

    return default
예제 #2
0
파일: config.py 프로젝트: bijij/Ditto
def env_var_constructor(loader: yaml.Loader,
                        node: yaml.ScalarNode) -> Optional[str]:
    if node.id != "scalar":
        raise TypeError("Expected a string")

    value = loader.construct_scalar(node)
    key = str(value)

    return os.getenv(key)
예제 #3
0
파일: yaml.py 프로젝트: con2/emrichen
def construct_tagless_yaml(loader: yaml.Loader, node: yaml.Node):
    # From yaml.constructor.BaseConstructor#construct_object
    if isinstance(node, yaml.ScalarNode):
        return loader.construct_scalar(node)
    elif isinstance(node, yaml.SequenceNode):
        return loader.construct_sequence(node)
    elif isinstance(node, yaml.MappingNode):
        return loader.construct_mapping(node)
    raise NotImplementedError('invalid node')
예제 #4
0
def construct_custom_class(cls, loader: yaml.Loader, node: yaml.Node):
    result = cls.__new__(cls)
    yield result
    if isinstance(node, yaml.ScalarNode):
        value = loader.construct_scalar(node)
    elif isinstance(node, yaml.SequenceNode):
        value = loader.construct_sequence(node)
    elif isinstance(node, yaml.MappingNode):
        value = loader.construct_mapping(node)
    else:
        assert False
    result.__init__(value)
예제 #5
0
    def inner(loader: yaml.Loader, node):
        value = loader.construct_scalar(node)
        for env_code in pattern.findall(value):
            env_name, _, env_type = env_code.partition(":")
            env = os.environ.get(env_name)
            if not env:
                return None
            value = value.replace(f"${{{env_code}}}", env)

            if env_type == "bool":
                return value.lower().strip() == "true"
            return types.get(env_type, str)(value)

        return value
예제 #6
0
def _env_var_constructor(loader: yaml.Loader, node: yaml.Node):
    '''Implements a custom YAML tag for loading optional environment variables.
    If the environment variable is set it returns its value.
    Otherwise returns `None`.

    Example usage:
        key: !ENV 'KEY'
    '''
    if node.id == 'scalar':  # type: ignore
        value = loader.construct_scalar(node)
        key = str(value)

    else:
        raise TypeError('Expected a string')

    return HiddenRepr(os.getenv(key))
예제 #7
0
def _env_yaml(loader: yaml.Loader, node: yaml.nodes.Node):
    """Extracts the environment variable from the node's value

    :param loader: the yaml loader
    :param node: the current node in the yaml
    :return: the parsed string that contains the value of the environment variable
    """

    value = loader.construct_scalar(node)
    match = _ENV_pattern.findall(value)  # to find all env variables in line
    if match:
        full_value = value
        for g in match:
            full_value = full_value.replace(f'${{{g}}}', os.environ.get(g, g))
        return full_value
    return value
예제 #8
0
def intrinsics_multi_constructor(  # pylint: disable=unused-argument
        loader: yaml.Loader, tag_prefix: str,
        node: yaml.Node) -> Dict[str, Any]:
    """YAML constructor to parse CloudFormation intrinsics.

    This will return a dictionary with key being the intrinsic name

    """
    # Get the actual tag name excluding the first exclamation
    tag = node.tag[1:]

    # Some intrinsic functions doesn't support prefix "Fn::"
    prefix = "Fn::"
    if tag in ["Ref", "Condition"]:
        prefix = ""

    cfntag = prefix + tag

    if tag == "GetAtt" and isinstance(node.value, str):
        # ShortHand notation for !GetAtt accepts Resource.Attribute format
        # while the standard notation is to use an array
        # [Resource, Attribute]. Convert shorthand to standard format
        value = node.value.split(".", 1)

    elif isinstance(node, yaml.ScalarNode):
        # Value of this node is scalar
        value = loader.construct_scalar(node)

    elif isinstance(node, yaml.SequenceNode):
        # Value of this node is an array (Ex: [1,2])
        value = cast(MutableSequence[Any], loader.construct_sequence(node))

    else:
        # Value of this node is an mapping (ex: {foo: bar})
        value = cast(MutableMapping[Any, Any], loader.construct_mapping(node))

    return {cfntag: value}
예제 #9
0
 def constructor(loader: yaml.Loader, node: yaml.Node):
     ids = [int(x) for x in loader.construct_scalar(node).split()]
     return Object(ids[-1], lambda: func(*ids))
예제 #10
0
 def _from_yaml(cls, loader: yaml.Loader,
                node: yaml.Node) -> "YamlModifier":
     """Load an internal yaml node parsing, defaulting to a scalar value."""
     value = loader.construct_scalar(typing.cast(yaml.ScalarNode, node))
     return cls(value)
예제 #11
0
 def _from_yaml(cls, loader: yaml.Loader,
                node: yaml.Node) -> "InjectString":
     """Load an internal yaml node parsing."""
     raw = loader.construct_scalar(typing.cast(yaml.ScalarNode, node))
     value = json.loads(typing.cast(str, raw).strip("\"'"))
     return cls(value)
예제 #12
0
def _path_constructor(loader: yaml.Loader, node):
    value = loader.construct_scalar(node)
    return Path(value)
 def _construct_config(self, loader: yaml.Loader, node: yaml.Node):
     key = loader.construct_scalar(node)
     return self.Config.get(key)
    def _construct_include(self, loader: yaml.Loader, node: yaml.Node):
        """Include file referenced at node."""

        identifier = loader.construct_scalar(node)
        declaration = self.read(identifier)
        return self.parse(declaration, identifier)
예제 #15
0
def env_constructor(loader: yaml.Loader, node: yaml.Node) -> str:
    value = loader.construct_scalar(node)
    if value not in os.environ:
        raise YAMLEnvVariableError(value)
    return os.environ.get(value)
예제 #16
0
def string_module_constructor(loader: yaml.Loader, node: yaml.Node) -> str:
    value = loader.construct_scalar(node)
    if value in POSSIBLE_SYMBOLS_VALUES:
        return getattr(string, value)
    raise YAMLStringValueError(value)
def time_constructor(loader: yaml.Loader, node: yaml.ScalarNode) -> time:
    value = loader.construct_scalar(node)
    data = time.fromisoformat(value)
    return data
예제 #18
0
def timedelta_constructor(loader: yaml.Loader,
                          node: yaml.ScalarNode) -> Optional[timedelta]:
    value = loader.construct_scalar(node)
    data = parse_timedelta(value)
    return data