Работа с XML в Go (Golang): полное руководство с примерами
Go (Golang) предлагает встроенную поддержку работы с XML через пакет encoding/xml. Этот пакет предоставляет мощные инструменты для парсинга (чтения), генерации (записи) и сериализации данных в формате XML. В отличие от JSON, XML требует более строгой структуры и поддержки пространств имен (namespaces), что делает encoding/xml особенно гибким.
В этой статье мы подробно разберем, как работать с XML в Go: от базового анмаршаллинга (преобразования XML в структуры Go) до создания сложных XML-документов с атрибутами и пространствами имен.
Основы: структуры и теги XML
Для сопоставления XML-элементов с полями структур Go используются специальные теги xml. Они определяют имя элемента, атрибуты и поведение при сериализации.
type Person struct {
XMLName xml.Name `xml:"person"`
ID int `xml:"id,attr"`
Name string `xml:"name"`
Age int `xml:"age"`
Email string `xml:"email,omitempty"`
Addresses []Address `xml:"address"`
}
type Address struct {
City string `xml:"city"`
Street string `xml:"street"`
ZipCode string `xml:"zip"`
}
xml:"person"— имя корневого элемента.xml:"id,attr"— поле становится атрибутом элемента.xml:"email,omitempty"— поле пропускается, если пустое.xml:"address"— массив будет сериализован как несколько вложенных элементов.
Парсинг XML: анмаршаллинг (Unmarshal)
Функция xml.Unmarshal преобразует XML-байты в структуру Go. Рассмотрим пример с нашим типом Person:
package main
import (
"encoding/xml"
"fmt"
)
func main() {
xmlData := `<person id="123">
<name>Иван Петров</name>
<age>30</age>
<email>ivan@example.com</email>
<address>
<city>Москва</city>
<street>Тверская, 1</street>
<zip>101000</zip>
</address>
</person>`
var p Person
err := xml.Unmarshal([]byte(xmlData), &p)
if err != nil {
fmt.Printf("Ошибка парсинга: %v\n", err)
return
}
fmt.Printf("ID: %d\n", p.ID)
fmt.Printf("Имя: %s\n", p.Name)
fmt.Printf("Возраст: %d\n", p.Age)
fmt.Printf("Город: %s\n", p.Addresses[0].City)
}
Вывод программы:
ID: 123
Имя: Иван Петров
Возраст: 30
Город: Москва
Генерация XML: маршаллинг (Marshal)
Для создания XML из структуры используется xml.Marshal или xml.MarshalIndent (с отступами).
func main() {
p := Person{
ID: 456,
Name: "Анна Смирнова",
Age: 25,
Email: "anna@example.com",
Addresses: []Address{
{City: "Санкт-Петербург", Street: "Невский, 10", ZipCode: "191186"},
},
}
output, err := xml.MarshalIndent(p, "", " ")
if err != nil {
fmt.Printf("Ошибка сериализации: %v\n", err)
return
}
fmt.Println(string(output))
}
Результат:
<person id="456">
<name>Анна Смирнова</name>
<age>25</age>
<email>anna@example.com</email>
<address>
<city>Санкт-Петербург</city>
<street>Невский, 10</street>
<zip>191186</zip>
</address>
</person>
Работа с пространствами имен (Namespaces)
XML-пространства имен обрабатываются через поле XMLName с атрибутом xmlns.
type Document struct {
XMLName xml.Name `xml:"doc"`
Title string `xml:"title"`
Content string `xml:"content"`
Lang string `xml:"xml:lang,attr"`
}
func main() {
doc := Document{
Title: "Пример",
Content: "Текст документа", Также в библиотеке
GraphQL Java: мощный инструмент для создания современных API на Java
Работа с Kafka в PHP: библиотеки, подключение и примеры кода
WireMock для Java: полное руководство с примерами
Hilt/Dagger для Kotlin: полное руководство с примерами
Email отправка на PHP: PHPMailer, SwiftMailer и mail() — полное руководство