Разработка и Конфигурация · 13 мин
Как прочитать XML-файл в 1С: пошаговое руководство с примерами
Практические способы чтения XML в 1С: ЧтениеXML, построитель DOM и XDTO. Примеры кода, проверка результата, типичные ошибки и ответы на вопросы.
XML — основной формат обмена данными в экосистеме 1С: через него выгружаются документы, справочники, ответы веб-сервисов, электронные накладные и отчёты в контролирующие органы. Поэтому задача «прочитать XML-файл» возникает у разработчика и внедренца постоянно — от простого разбора файла выгрузки до полноценной интеграции с внешней системой.
В платформе 1С:Предприятие есть три основных механизма чтения XML: потоковый объект ЧтениеXML, объектная модель документа ЧтениеDOM и технология XDTO для работы по схеме. У каждого свои сценарии применения, ограничения по памяти и требования к структуре файла. Неправильный выбор механизма — частая причина медленной обработки больших файлов и ошибок «не найден элемент».
Ниже разобраны все три подхода с рабочим кодом, критериями выбора, способами проверки результата и типичными ошибками. Материал подходит для управляемых и обычных форм, файловых и клиент-серверных баз на платформе 8.3.
Какие способы чтения XML есть в 1С и как выбрать
Платформа предлагает три независимых механизма, и выбор между ними определяется размером файла, наличием схемы (XSD) и тем, как вы собираетесь обходить данные — последовательно или с произвольным доступом к узлам.
ЧтениеXML — потоковый парсер: файл читается последовательно, узел за узлом, без загрузки всего документа в память. Это единственный безопасный вариант для файлов в сотни мегабайт. Минус — нельзя «вернуться назад» или сразу получить вложенный элемент по пути: весь обход и логику вложенности вы реализуете сами.
ЧтениеDOM (Document Object Model) — файл целиком загружается в память в виде дерева объектов. Удобно, когда нужно многократно обращаться к разным веткам, искать узлы по имени и проходить документ в произвольном порядке. Ограничение — потребление памяти: большой файл может привести к аварийному завершению сеанса.
XDTO (XML Data Transfer Objects) — механизм работы с XML по формальной схеме. Платформа сама проверяет типы, обязательность элементов и преобразует XML в объекты. Это основной способ для регламентированных форматов: электронных документов, обмена с банками, веб-сервисов. Требует наличия или готового пакета XDTO в конфигурации, или XSD-схемы файла.
Сравнение способов чтения XML
Большие файлы, потоковая обработка, минимум памяти. Ограничение: только последовательный обход, логика вложенности вручную.
Небольшие и средние файлы, нужен произвольный доступ к узлам и поиск по дереву. Ограничение: весь документ в памяти.
Обмен по XSD-схеме, регламентированные форматы, веб-сервисы. Ограничение: нужна схема и соответствие файла ей.
Чтение XML через объект ЧтениеXML
Это базовый и самый универсальный способ. Объект создаётся конструктором, файл открывается методом ОткрытьФайл(), далее в цикле вызывается Прочитать(), который перемещает курсор к следующему узлу. Тип текущего узла определяется через свойство ТипУзла.
Минимальный рабочий пример чтения файла и обхода всех элементов:
Чтение = Новый ЧтениеXML;
Чтение.ОткрытьФайл("C:\Обмен\data.xml");
Пока Чтение.Прочитать() Цикл
Если Чтение.ТипУзла = ТипУзлаXML.НачалоЭлемента Тогда
ИмяУзла = Чтение.Имя;
// обработка начала элемента
ИначеЕсли Чтение.ТипУзла = ТипУзлаXML.Текст Тогда
Значение = Чтение.Значение;
// обработка текста внутри элемента
КонецЕсли;
КонецЦикла;
Чтение.Закрыть();
Обратите внимание на три обязательных момента. Во-первых, после окончания работы вызывайте Закрыть() — иначе файл останется заблокированным процессом 1С и его нельзя будет удалить или перезаписать. Во-вторых, текстовое содержимое элемента приходит отдельным узлом типа Текст, а не вместе с началом элемента. В-третьих, атрибуты читаются через ПолучитьАтрибут("ИмяАтрибута") или перебором КоличествоАтрибутов(), пока курсор стоит на начале элемента.
Если структура файла известна, удобнее использовать метод ПрочитатьЭлемент() или проверку Чтение.Имя = "Номенклатура" внутри цикла, отслеживая вложенность через счётчик уровня или конец элемента (ТипУзлаXML.КонецЭлемента).
- 1Создайте объект: Чтение = Новый ЧтениеXML
- 2Откройте файл: Чтение.ОткрытьФайл(ПутьКФайлу)
- 3Организуйте цикл Пока Чтение.Прочитать() Цикл
- 4Внутри цикла проверяйте Чтение.ТипУзла и Чтение.Имя
- 5Считывайте атрибуты через ПолучитьАтрибут() на начале элемента
- 6После цикла вызовите Чтение.Закрыть()
- 7Проверьте, что данные попали в структуру или таблицу значений
Чтение XML через DOM (объектная модель документа)
DOM подходит, когда файл небольшой и нужно гибко обращаться к узлам: найти все элементы с определённым именем, прочитать дочерние элементы конкретного узла, пройти дерево в любом порядке. Документ строится через ПостроительDOM.
Чтение = Новый ЧтениеXML;
Чтение.ОткрытьФайл("C:\Обмен\data.xml");
Построитель = Новый ПостроительDOM;
Документ = Построитель.Прочитать(Чтение);
Чтение.Закрыть();
Узлы = Документ.ПолучитьЭлементыПоИмени("Товар");
Для Каждого Узел Из Узлы Цикл
Наименование = Узел.ПолучитьАтрибут("Наименование");
// обработка узла
КонецЦикла;
Ключевые методы работы с деревом: ЭлементДокумента — корневой элемент, ДочерниеУзлы — список вложенных узлов, ПолучитьЭлементыПоИмени() — поиск по имени элемента во всём документе, ТекстовоеСодержимое — весь текст узла одной строкой. Учтите, что текстовые узлы тоже входят в ДочерниеУзлы, поэтому при переборе проверяйте ТипУзлаDOM.
Главный риск DOM — память. Файл в несколько десятков мегабайт в виде дерева объектов может занять в разы больше оперативной памяти. Для серверного кода это опасно: превышение лимита приводит к аварийному завершению рабочего процесса и затрагивает других пользователей. Если размер файла заранее неизвестен, используйте потоковое ЧтениеXML.
Чтение XML через XDTO по схеме
XDTO применяется, когда формат файла формально описан: есть XSD-схема или в конфигурации уже добавлен пакет XDTO (например, для форматов электронных документов в типовых решениях). Платформа сама проверит соответствие файла схеме и вернёт типизированные объекты.
Чтение = Новый ЧтениеXML;
Чтение.ОткрытьФайл("C:\Обмен\order.xml");
Фабрика = ФабрикаXDTO; // или собственная фабрика из XSD
ОбъектXDTO = Фабрика.ПрочитатьXML(Чтение);
Чтение.Закрыть();
НомерДокумента = ОбъектXDTO.Номер;
Если схемы в конфигурации нет, её можно создать из XSD-файла: в конфигураторе добавьте пакет XDTO и импортируйте схему, либо программно постройте фабрику через СоздатьФабрикуXDTO(). Дальше обращение к данным идёт как к свойствам объекта, коллекции повторяющихся элементов доступны как списки XDTO.
Плюс подхода — валидация: если обязательный элемент отсутствует или тип не совпадает, платформа выдаст понятную ошибку ещё на этапе чтения. Минус — жёсткая привязка к схеме: любое отклонение файла от XSD (лишний элемент, другое пространство имён) приведёт к ошибке, даже если данные в файле фактически корректны.
Чтение XML из строки, из макета и из веб-сервиса
Не всегда XML находится в файле на диске. Часто данные приходят как строка — из HTTP-ответа, из поля базы данных, из макета конфигурации. В этом случае вместо ОткрытьФайл() используется метод УстановитьСтроку():
Чтение = Новый ЧтениеXML;
Чтение.УстановитьСтроку(СтрокаXML);
// далее обход аналогично
Чтение из HTTP-ответа
При обращении к веб-сервису тело ответа получают методом ПолучитьТелоКакСтроку() объекта HTTPОтвет, затем передают в ЧтениеXML или в ФабрикаXDTO.ПрочитатьXML(). Перед разбором проверяйте код состояния ответа: при ошибке сервера в теле может быть HTML или пустая строка, и попытка разобрать её как XML даст исключение «Ошибка разбора XML».
Чтение из макета
Тестовые и эталонные XML-данные удобно хранить в макете типа «Текстовый документ»: Текст = ПолучитьМакет("ДанныеXML").ПолучитьТекст(), далее — УстановитьСтроку(Текст). Это удобно для отладки обработчика без внешних файлов.
Кодировка, пространства имён и типичные ошибки
Большинство проблем при чтении XML связано не с логикой обхода, а с особенностями самого файла. Разберём три самых частых источника сбоев.
Кодировка. ЧтениеXML по умолчанию определяет кодировку из объявления XML (<?xml version="1.0" encoding="UTF-8"?>). Если файл в ANSI (Windows-1251), а объявление отсутствует или неверно, кириллица превратится в нечитаемые символы. Решение — открыть файл через ЧтениеТекста с явной кодировкой и передать строку в ЧтениеXML, либо указать кодировку в параметрах открытия.
Пространства имён. Если элементы записаны как <ns:Товар xmlns:ns="...">, свойство Имя вернёт «Товар», а ИмяСПрефиксом — «ns:Товар». При сравнении имён учитывайте это, иначе условие Чтение.Имя = "ns:Товар" никогда не сработает.
Битые файлы. Обрыв файла при выгрузке, лишний символ до объявления XML, BOM в середине строки — всё это вызывает «Ошибку разбора XML» с указанием позиции. Позиция в сообщении об ошибке (строка, колонка) — первое место, куда стоит смотреть при диагностике: откройте файл в текстовом редакторе с нумерацией строк.
Как проверить результат чтения
После разбора файла убедитесь, что данные действительно извлечены, прежде чем записывать их в базу. Минимальный контроль — количество обработанных элементов: если файл содержит тысячу товаров, а цикл нашёл ноль, значит, условие по имени узла не сработало.
Практичный приём — на этапе отладки выводить в сообщения имя каждого найденного элемента и значения ключевых атрибутов. Для больших файлов ограничьте вывод первыми десятью элементами, чтобы не переполнить окно сообщений. Второй уровень контроля — сверка контрольных сумм: количество строк, итоговая сумма документов в файле против полученных данных.
При записи данных в базу оборачивайте загрузку в транзакцию: если на середине файла возникнет ошибка, база не останется в полузаполненном состоянии. Для повторяющихся загрузок реализуйте поиск существующих объектов по ключевым полям (код, GUID, номер и дата документа), иначе каждый запуск будет создавать дубликаты.
Как проверить результат
Совпадает с ожидаемым числом записей в файле
Ноль или значительно меньше — проверяйте имена узлов и пространства имён
Текст читается корректно
Нечитаемые символы — проблема с кодировкой файла
Файл можно удалить или перезаписать
Файл заблокирован — не вызван метод Закрыть()
Объекты созданы/обновлены без дубликатов
Дубли при повторном запуске — нет поиска существующих объектов
Перед написанием обработчика откройте XML-файл в браузере или редакторе и выпишите точные имена элементов, их вложенность и атрибуты. Большинство ошибок «данные не читаются» вызваны расхождением предполагаемой и реальной структуры файла, а не кодом.
Частые вопросы
Чем ЧтениеXML отличается от ЧтениеТекста для XML-файлов?
ЧтениеТекста возвращает содержимое файла как обычную строку — разбирать структуру придётся вручную. ЧтениеXML — это парсер: он понимает узлы, атрибуты и вложенность, позволяет обходить документ по элементам. Для разбора XML всегда используйте ЧтениеXML, а ЧтениеТекста применяйте только как промежуточный шаг при проблемах с кодировкой.
Как прочитать XML-файл на клиенте в тонком или веб-клиенте?
На тонком клиенте объекты ЧтениеXML и ПостроительDOM доступны, но путь к файлу должен быть доступен с клиентской машины. Если файл лежит на сервере, передавайте его через хранилище значений или временное хранилище и обрабатывайте в серверной процедуре. В веб-клиенте прямой доступ к файловой системе ограничен — используйте диалоги помещения файлов.
Что делать, если файл очень большой и обработка занимает много времени?
Используйте потоковое ЧтениеXML и записывайте данные в базу порциями с фиксацией транзакции, а не одной транзакцией на весь файл. Длительную обработку выносите в фоновое задание, чтобы не блокировать сеанс пользователя. Избегайте в цикле запросов к базе на каждый элемент — накапливайте данные в таблице значений и выполняйте пакетную обработку.
Можно ли прочитать XML без знания его структуры заранее?
Да. В цикле ЧтениеXML выводите тип узла, имя и значение — так вы получите полную карту документа. DOM позволяет рекурсивно обойти дерево через ДочерниеУзлы без привязки к конкретным именам. XDTO без схемы применить нельзя — этот механизм требует описания формата.
Как прочитать значение атрибута элемента?
Когда курсор ЧтениеXML стоит на начале элемента, вызовите Чтение.ПолучитьАтрибут("ИмяАтрибута") — метод вернёт значение или Неопределено, если атрибута нет. Альтернатива — перебор по индексу через КоличествоАтрибутов() и ИмяАтрибута(Индекс). В DOM атрибут читается методом ПолучитьАтрибут() у узла элемента.
Почему возникает ошибка «Ошибка разбора XML» сразу при открытии файла?
Чаще всего файл не является валидным XML: перед объявлением <?xml?> есть посторонние символы или BOM, файл обрезан при выгрузке, либо это вообще не XML (например, HTML-страница ошибки). Откройте файл в текстовом редакторе и посмотрите первые строки и позицию, указанную в тексте ошибки.
Что важно запомнить
Для больших файлов используйте потоковое ЧтениеXML, для произвольного доступа к узлам — ЧтениеDOM с ПостроительDOM, для обмена по схеме — XDTO. Всегда закрывайте чтение методом Закрыть(), проверяйте кодировку и пространства имён, а результат сверяйте по количеству элементов до записи в базу.