...

Source file src/github.com/letsencrypt/boulder/strictyaml/yaml.go

Documentation: github.com/letsencrypt/boulder/strictyaml

     1  // Package strictyaml provides a strict YAML unmarshaller based on `go-yaml/yaml`
     2  package strictyaml
     3  
     4  import (
     5  	"bytes"
     6  	"errors"
     7  	"fmt"
     8  	"io"
     9  
    10  	"gopkg.in/yaml.v3"
    11  )
    12  
    13  // Unmarshal takes a byte array and an interface passed by reference. The
    14  // d.Decode will read the next YAML-encoded value from its input and store it in
    15  // the value pointed to by yamlObj. Any config keys from the incoming YAML
    16  // document which do not correspond to expected keys in the config struct will
    17  // result in errors.
    18  //
    19  // TODO(https://github.com/go-yaml/yaml/issues/639): Replace this function with
    20  // yaml.Unmarshal once a more ergonomic way to set unmarshal options is added
    21  // upstream.
    22  func Unmarshal(b []byte, yamlObj interface{}) error {
    23  	r := bytes.NewReader(b)
    24  
    25  	d := yaml.NewDecoder(r)
    26  	d.KnownFields(true)
    27  
    28  	// d.Decode will mutate yamlObj
    29  	err := d.Decode(yamlObj)
    30  
    31  	if err != nil {
    32  		// io.EOF is returned when the YAML document is empty.
    33  		if errors.Is(err, io.EOF) {
    34  			return fmt.Errorf("unmarshalling YAML, bytes cannot be nil: %w", err)
    35  		}
    36  		return fmt.Errorf("unmarshalling YAML: %w", err)
    37  	}
    38  
    39  	// As bytes are read by the decoder, the length of the byte buffer should
    40  	// decrease. If it doesn't, there's a problem.
    41  	if r.Len() != 0 {
    42  		return fmt.Errorf("yaml object of size %d bytes had %d bytes of unexpected unconsumed trailers", r.Size(), r.Len())
    43  	}
    44  
    45  	return nil
    46  }
    47  

View as plain text