<SYSTEM_TASK:>
Solve the following problem using Python, implementing the functions described below, one line at a time
<END_TASK>
<USER_TASK:>
Description:
 def _set_with_metadata(self, name, value, layer=None, source=None):
 """Set a value in the named layer with the given source. Parameters name : str The name of the value value The value to store layer : str, optional The name of the layer to store the value in. If none is supplied then the value will be stored in the outermost layer. source : str, optional The source to attribute the value to. Raises ------ TypeError if the ConfigTree is frozen """


        if self._frozen:
            raise TypeError('Frozen ConfigTree does not support assignment')

        if isinstance(value, dict):
            if name not in self._children or not isinstance(self._children[name], ConfigTree):
                self._children[name] = ConfigTree(layers=list(self._layers))
            self._children[name].update(value, layer, source)
        else:
            if name not in self._children or not isinstance(self._children[name], ConfigNode):
                self._children[name] = ConfigNode(list(self._layers))
            child = self._children[name]
            child.set_value(value, layer, source)