diff options
| author | Gustavo Niemeyer <gustavo@niemeyer.net> | 2012-01-24 01:10:32 -0200 |
|---|---|---|
| committer | Gustavo Niemeyer <gustavo@niemeyer.net> | 2012-01-24 01:10:32 -0200 |
| commit | 0442087f93d49dec95cd327efbc8c760484ac8bb (patch) | |
| tree | 4cd83269db3ed504f0b598efbcdaed4a6d884a3f /src/pkg/encoding/xml/read.go | |
| parent | 6d7e9382b49cbb0969f352af10def6c84740a0d3 (diff) | |
| download | go-0442087f93d49dec95cd327efbc8c760484ac8bb.tar.xz | |
encoding/xml: bring API closer to other packages
Includes gofix module. The only case not covered should be
xml.Unmarshal, since it remains with a similar interface, and
would require introspecting the type of its first argument
better.
Fixes #2626.
R=golang-dev, rsc, gustavo
CC=golang-dev
https://golang.org/cl/5574053
Diffstat (limited to 'src/pkg/encoding/xml/read.go')
| -rw-r--r-- | src/pkg/encoding/xml/read.go | 61 |
1 files changed, 27 insertions, 34 deletions
diff --git a/src/pkg/encoding/xml/read.go b/src/pkg/encoding/xml/read.go index 78e02018cf..8b23fd58a0 100644 --- a/src/pkg/encoding/xml/read.go +++ b/src/pkg/encoding/xml/read.go @@ -7,7 +7,6 @@ package xml import ( "bytes" "errors" - "io" "reflect" "strconv" "strings" @@ -20,10 +19,10 @@ import ( // See package json for a textual representation more suitable // to data structures. -// Unmarshal parses an XML element from r and uses the -// reflect library to fill in an arbitrary struct, slice, or string -// pointed at by val. Well-formed data that does not fit -// into val is discarded. +// Unmarshal parses the XML-encoded data and stores the result in +// the value pointed to by v, which must be an arbitrary struct, +// slice, or string. Well-formed data that does not fit into v is +// discarded. // // For example, given these definitions: // @@ -59,7 +58,7 @@ import ( // <address>123 Main Street</address> // </result> // -// via Unmarshal(r, &result) is equivalent to assigning +// via Unmarshal(data, &result) is equivalent to assigning // // r = Result{ // xml.Name{Local: "result"}, @@ -157,18 +156,26 @@ import ( // Unmarshal maps an XML element to a pointer by setting the pointer // to a freshly allocated value and then mapping the element to that value. // -func Unmarshal(r io.Reader, val interface{}) error { - v := reflect.ValueOf(val) - if v.Kind() != reflect.Ptr { +func Unmarshal(data []byte, v interface{}) error { + return NewDecoder(bytes.NewBuffer(data)).Decode(v) +} + +// Decode works like xml.Unmarshal, except it reads the decoder +// stream to find the start element. +func (d *Decoder) Decode(v interface{}) error { + return d.DecodeElement(v, nil) +} + +// DecodeElement works like xml.Unmarshal except that it takes +// a pointer to the start XML element to decode into v. +// It is useful when a client reads some raw XML tokens itself +// but also wants to defer to Unmarshal for some elements. +func (d *Decoder) DecodeElement(v interface{}, start *StartElement) error { + val := reflect.ValueOf(v) + if val.Kind() != reflect.Ptr { return errors.New("non-pointer passed to Unmarshal") } - p := NewParser(r) - elem := v.Elem() - err := p.unmarshal(elem, nil) - if err != nil { - return err - } - return nil + return d.unmarshal(val.Elem(), start) } // An UnmarshalError represents an error in the unmarshalling process. @@ -176,22 +183,8 @@ type UnmarshalError string func (e UnmarshalError) Error() string { return string(e) } -// The Parser's Unmarshal method is like xml.Unmarshal -// except that it can be passed a pointer to the initial start element, -// useful when a client reads some raw XML tokens itself -// but also defers to Unmarshal for some elements. -// Passing a nil start element indicates that Unmarshal should -// read the token stream to find the start element. -func (p *Parser) Unmarshal(val interface{}, start *StartElement) error { - v := reflect.ValueOf(val) - if v.Kind() != reflect.Ptr { - return errors.New("non-pointer passed to Unmarshal") - } - return p.unmarshal(v.Elem(), start) -} - // Unmarshal a single XML element into val. -func (p *Parser) unmarshal(val reflect.Value, start *StartElement) error { +func (p *Decoder) unmarshal(val reflect.Value, start *StartElement) error { // Find start element if we need it. if start == nil { for { @@ -484,9 +477,9 @@ func copyValue(dst reflect.Value, src []byte) (err error) { // unmarshalPath walks down an XML structure looking for wanted // paths, and calls unmarshal on them. // The consumed result tells whether XML elements have been consumed -// from the Parser until start's matching end element, or if it's +// from the Decoder until start's matching end element, or if it's // still untouched because start is uninteresting for sv's fields. -func (p *Parser) unmarshalPath(tinfo *typeInfo, sv reflect.Value, parents []string, start *StartElement) (consumed bool, err error) { +func (p *Decoder) unmarshalPath(tinfo *typeInfo, sv reflect.Value, parents []string, start *StartElement) (consumed bool, err error) { recurse := false Loop: for i := range tinfo.fields { @@ -550,7 +543,7 @@ Loop: // Read tokens until we find the end element. // Token is taking care of making sure the // end element matches the start element we saw. -func (p *Parser) Skip() error { +func (p *Decoder) Skip() error { for { tok, err := p.Token() if err != nil { |
