func (d Data) String() string {
	raw, err := yaml.Marshal(d)
	if err != nil {
		return fmt.Sprintf("<config.data: failed to marshal: %v>", err)
	}
	return string(raw)
}
String returns configuration data as a string.
package config
import (
	"fmt"
	"io/ioutil"
	"sigs.k8s.io/yaml"
	"strings"
)
type Data map[string]interface{}
func DataFromObject(obj interface{}) (Data, error) {
	raw, err := yaml.Marshal(obj)
	if err != nil {
		return nil, configError("failed to marshal object %T to data: %v", obj, err)
	}
	data := make(Data)
	if err = yaml.Unmarshal(raw, &data); err != nil {
		return nil, configError("failed to unmarshal object %T to data: %v", obj, err)
	}
	return data, nil
}
func DataFromStringMap(smap map[string]string) (Data, error) {
	data := make(Data)
	for key, val := range smap {
		var obj interface{}
		if err := yaml.Unmarshal([]byte(val), &obj); err != nil {
			return nil, configError("failed to unmarshal data from map: %v", err)
		}
		data[key] = obj
	}
	return data, nil
}
func DataFromFile(path string) (Data, error) {
	raw, err := ioutil.ReadFile(path)
	if err != nil {
		return nil, configError("failed to read file %q: %v", path, err)
	}
	data := make(Data)
	if err := yaml.Unmarshal(raw, &data); err != nil {
		return nil, configError("failed to load configuration from file %q: %v", path, err)
	}
	return data, nil
}
func (d Data) copy() Data {
	data := make(Data)
	for key, value := range d {
		data[key] = value
	}
	return data
}
func (d Data) split(hasChild func(string) bool) (Data, Data) {
	mod, sub := make(Data), make(Data)
	for key, val := range d {
		if hasChild(key) || strings.IndexByte(key, '.') != -1 {
			sub[key] = val
		} else {
			mod[key] = val
		}
	}
	return mod, sub
}
func (d Data) pick(key string, removePicked bool) (Data, error) {
	var data Data
	var err error
	if obj, ok := d[key]; ok {
		data, err = DataFromObject(obj)
		if err != nil {
			return nil, err
		}
		if removePicked {
			delete(d, key)
		}
	}
	for k, v := range d {
		split := strings.Split(k, ".")
		if len(split) > 1 && split[0] == key {
			if data == nil {
				data = make(Data)
			}
			subkey := strings.Join(split[1:], ".")
			if _, ok := data[subkey]; ok {
				return nil, configError("dotted key %q conflicts with nested key %q", k, subkey)
			}
			data[subkey] = v
			if removePicked {
				delete(d, k)
			}
		}
	}
	return data, nil
}