0

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!

2 Answers 2

2

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"`
}
Sign up to request clarification or add additional context in comments.

5 Comments

Hi Stéphane, your suggestion works, thanks! But how about the attributes? Do you have any clue about how to load these values?
@jsfelipearaujo, sorry for being glib, but have you read the package documentation? SO is not a service for reciting it, really. In particular, see the process of unmarshaling.
@kostix, yes I did. But there is no mention about how to read attributes from sub-elements using the path syntax.
@jsfelipearaujo, «If the XML element has an attribute whose name matches a struct field name with an associated tag containing ",attr" or the explicit name in a struct field tag of the form "name,attr", Unmarshal records the attribute value in that field.» and then «If the XML element contains a sub-element whose name matches the prefix of a tag formatted as "a" or "a>b>c", <…>»–the 1st explains name,attr, and the second explains how to format name there to refer to a nested element.
0

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)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.