Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

encoding/xml: `,innerxml` makes light of namespaces. #14467

Open
HinataYanagi opened this issue Feb 22, 2016 · 3 comments

Comments

Projects
None yet
3 participants
@HinataYanagi
Copy link

commented Feb 22, 2016

See the example. The result is obviously not what we wish. We have no way we can obtain and recover the context, namely the prefix-namespace correspondence, where the fragment is extracted. I found xml.go naively accumulating input stream in saved while ,innerxml is effective. The best solution is like the below:

buffer := new(bytes.Buffer)
encoder := xml.NewEncoder(buffer)

// ...

for {
  token, err := Token()
  // ...
  encoder.EncodeToken(token)
}

// ...

encoder.Flush()
saveXMLData = buffer.Bytes()

Namespace-aware ,innerxml is rather expensive, so we may as well have a new flag. Millions of extensible guys are eager for a politic decision.

@HinataYanagi HinataYanagi changed the title encoding/xml: `,innerxml` making light of namespaces encoding/xml: `,innerxml` makes light of namespaces. Feb 22, 2016

@bradfitz bradfitz added this to the Unplanned milestone Apr 10, 2016

@bradfitz

This comment has been minimized.

Copy link
Member

commented Apr 10, 2016

See related bugs: #13400 and #14407

@HinataYanagi

This comment has been minimized.

Copy link
Author

commented Apr 10, 2016

Namespaces are cumbersome though essential after all. encoding/xml seems to have fundamental defects.

@iWdGo

This comment has been minimized.

Copy link
Contributor

commented Apr 22, 2018

Reading the namespace of a field can only be done at struct level using the XMLName field. The Unmarshal documentation specifies that

Unmarshal maps an XML element to a struct using the following rules. In the rules, the tag of a field refers to the value associated with the key 'xml' in the struct field's tag (see the example above).`

The storage of the namespace requires the XMLName field in the struct of the XML element. In your example, p is the field tag. So the following structure

/* Space is stored at struct level B and tag field p is read correctly */
	type B struct {
		XMLName xml.Name // To store the name space of the struct
		Content string `xml:"p"` // p tag is the field tag
	}
	type A struct {
		B B `xml:""`  // required to ensure that namespace is stored
	}

reads correctly
<A xmlns:x="urn:"><x:B><p>Go does not spoil its namespace</p></x:B></A>

The absence of the namespace on the B tag means that no default namespace applies to the inner tags
(https://www.w3.org/TR/xml-names/#defaulting) which looks unwanted in this case. Put it differently, the namespace of a field needs to be at the struct XML tag level to be readable.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.