Хоть и некропост, но я всё же дам ответ
В описании типа есть опечатка
type XMLProfile struct {
XMLName xml.Name `xml:"profile,omitempty"`
ProfileName string `xml:"profile_name",omitempty`
Fields []*XMLField `xml:"field,omitempty"`
}
Конкретно здесь: `xml:"profile_name
",omitempty`
Go не позволяет ошибаться в мета-информации структур, вот правильный вариант:
`xml:"profile_name
,omitempty"` - сначала бэктик, затем без пробелов: метка типа данных (xml), двоеточие, кавычки, имя в xml, запятая, дополнительные теги, кавычки (если нужно задать описание и для json - ставим пробел, повторяем всё то же самое), в завершении снова бэктик
Вот и весь фикс :)
Финальный код:
package main
import (
"encoding/json"
"encoding/xml"
"io/ioutil"
"log"
"os"
)
type XMLProfile struct {
XMLName xml.Name `xml:"profile,omitempty"`
ProfileName string `xml:"profile_name,omitempty"`
Fields []*XMLField `xml:"field,omitempty"`
}
type XMLField struct {
Name string `xml:"name,omitempty"`
Type string `xml:"type,omitempty"`
Value string `xml:"value,omitempty"`
}
func main() {
file, err := os.Open("example.xml")
if err != nil {
log.Println(err)
}
defer file.Close()
decoder := xml.NewDecoder(file)
for {
t, _ := decoder.Token()
if t == nil {
break
}
switch et := t.(type) {
case xml.StartElement:
if et.Name.Local == "profile" {
var object XMLProfile
decoder.DecodeElement(&object, &et)
resultData := map[string]map[string]string{
object.ProfileName: map[string]string{},
}
for _, val := range object.Fields {
resultData[object.ProfileName][val.Name] = val.Value
}
if out, err := json.MarshalIndent(resultData, "", " "); err != nil {
panic(err)
} else {
_ = ioutil.WriteFile("test.json", out, 0644)
}
}
}
}
}