jsfelipearaujo
jsfelipearaujo

Reputation: 25

Decode XML string into struct

I've the following xml:

<DOC>
<SubGroup1>
    <Value1>ABC123</Value1>
    <Value2>ABC123</Value2>
    <Value3>ABC123</Value3>
    <Value4>ABC123</Value4>
</SubGroup1>
<SubGroup2>
    <TheTag MyTagAttr="ABC123">
        <Value1>ABC123</Value1>
        <Value2>ABC123</Value2>
        <Value3>ABC123</Value3>
        <Value4 MyTagAttr="ABC123">ABC123</Value4>
        <Value5>ABC123</Value5>
        <Value6>ABC123</Value6>
        <Value7>ABC123</Value7>
        <Value8>ABC123</Value8>
        <Value9>ABC123</Value9>
    </TheTag>
</SubGroup2>
</DOC>

And I need to decode into this struct:

type TheTag struct {
    XMLName xml.Name `xml:"SubGroup2>TheTag"`

    Value1  string  `xml:"Value1"`
    Value2  string  `xml:"Value2"`
}

But I'm not able to decode properly this subelement into the struct.

I'm getting the following error:

error decoding message content: %!w(xml.UnmarshalError=expected element type <SubGroup2>TheTag> but have <DOC>)

My code is available here on Go Playgroud: https://go.dev/play/p/O688qTBARJm

Thanks in advance!

Upvotes: 0

Views: 60

Answers (2)

Alexandr Kamenev
Alexandr Kamenev

Reputation: 74

You can use the library github.com/clbanning/mxj

xmlBytes = []byte("<DOC>...</DOC>")
xmlStruct, err := mxj.NewMapXml(xmlBytes)
if err != nil {
  // handle error
}
theTag, err := xmlStruct.ValuesForPath("DOC.SubGroup2.TheTag")
if err != nil {
  // Do not exist "TheTag"
}
theTagInterface := theTag.(map[string]interface{})
myTagAttr := theTagInterface["-MyTagAttr"].(string)

val4, err := xmlStruct.ValuesForPath("DOC.SubGroup2.TheTag.Value4")
if err != nil {
  // Do not exist "Value4"
}
theVal4Interface := val4.(map[string]interface{})
myVal4Attr := theVal4Interface["-MyTagAttr"].(string)

Upvotes: 0

You should probably move the tags.

type TheTag struct {
  XMLName xml.Name `xml:"DOC"`

  Value1 string `xml:"SubGroup2>TheTag>Value1"`
  Value2 string `xml:"SubGroup2>TheTag>Value2"`
}

Upvotes: 2

Related Questions