Возникает задача автоматической обработки данных из файлов Excel, которые поступают в устаревшем формате XLS (Excel 97-2003). При попытке прочитать такой файл с помощью COM-объекта в 1С могут возникать ошибки, или же код просто не видит данные, хотя с форматом XLSX все работает корректно. Рассмотрим, как решить эту проблему: программно преобразовать файл в современный формат XLSX или использовать альтернативные способы чтения данных.
Первое, что может прийти в голову, — это просто сменить расширение файла с .xls на .xlsx с помощью функции ПереместитьФайл(). Это в корне неверный подход. Смена расширения не меняет внутреннюю структуру файла. Давайте разберемся в причинах.
Форматы XLS и XLSX принципиально разные:
.xlsx файл в .zip и открыв его архиватором.Поэтому, просто переименовав файл, мы не превратим бинарную структуру в архив с XML. Excel, открывая такой файл, определит несоответствие содержимого расширению и либо выдаст ошибку, либо попытается восстановить данные, но для программной обработки через COM-объект такой файл будет "битым".
Самый надежный способ корректно преобразовать файл — это использовать для этого сам Excel через COM-соединение. Если файлов много, удобнее использовать конвертер из xls в xlsx. Мы программно откроем исходный XLS-файл и дадим Excel команду сохранить его в новом формате XLSX.
Для этого используется метод SaveAs объекта Workbook, которому нужно передать путь к новому файлу и числовой код формата. Для формата XLSX (Excel Workbook) используется код 51.
Посмотрим на пример кода:
Процедура КонвертироватьФайлВXLSX(ПутьКФайлуXLS, ПутьКНовомуФайлуXLSX)
Попытка
Эксель = Новый COMОбъект("Excel.Application"); // Если на этом этапе возникает ошибка, изучите статью, почему не работает COM
// Скрываем окно Excel и отключаем системные сообщения
Эксель.Visible = Ложь;
Эксель.DisplayAlerts = Ложь;
Исключение
Сообщить("Не удалось запустить Excel. Проверьте, что он установлен на сервере. " + ОписаниеОшибки());
Возврат;
КонецПопытки
Попытка
// Открываем исходный XLS файл
Книга = Эксель.Workbooks.Open(ПутьКФайлуXLS);
// Сохраняем книгу в новом формате XLSX
// 51 - это константа VBA xlOpenXMLWorkbook, соответствующая формату XLSX
Книга.SaveAs(ПутьКНовомуФайлуXLSX, 51);
// Закрываем книгу без сохранения изменений (мы их уже сохранили в новый файл)
Книга.Close(Ложь);
Сообщить("Файл успешно сконвертирован: " + ПутьКНовомуФайлуXLSX);
Исключение
Сообщить("Ошибка при конвертации файла: " + ОписаниеОшибки());
КонецПопытки;
// Обязательно закрываем приложение Excel, чтобы не оставлять "висящих" процессов
Эксель.Quit();
КонецПроцедуры
После выполнения этой процедуры вы получите корректный XLSX-файл, который уже можно будет обрабатывать вашим основным кодом, читающим данные.
Платформа 1С имеет собственный мощный инструмент для работы с таблицами, который умеет читать файлы Excel без участия самого Excel. Это объект ТабличныйДокумент. Этот способ является предпочтительным, так как:
Использовать его очень просто:
Процедура ПрочитатьДанныеЧерезТабличныйДокумент(ПутьКФайлу)
ТабДок = Новый ТабличныйДокумент;
Попытка
ТабДок.Прочитать(ПутьКФайлу, СпособЧтенияЗначенийТабличногоДокумента.Значение);
Исключение
Сообщить("Не удалось прочитать файл. " + ОписаниеОшибки());
Возврат;
КонецПопытки;
// Теперь можно обходить ячейки и получать из них данные
// Например, получим значение из 17-й строки и 2-й колонки
// Синтаксис "R17C2" означает Row 17 (строка), Column 2 (колонка)
ФИО = ТабДок.Область("R17C2").Текст;
Количество = ТабДок.Область("R17C4").Значение; // Можно получить и значение, если это число
Сообщить("Прочитано ФИО: " + ФИО);
// Дальнейший обход документа в цикле
// ...
КонецПроцедуры
Важный момент: иногда встречаются XLS-файлы сложной структуры или с повреждениями, которые ТабличныйДокумент может прочитать некорректно или не прочитать вовсе. В таких случаях стоит вернуться к методу с COM или попробовать следующий вариант.
Этот метод позволяет обращаться к листу Excel как к таблице базы данных, используя SQL-подобные запросы. Он часто работает быстрее, чем COM-автоматизация, и также не требует установленного Microsoft Office. Нужны только специальные драйверы OLEDB, которые обычно можно скачать с сайта Microsoft (Microsoft Access Database Engine Redistributable).
Ключевое отличие при работе с XLS и XLSX — это строка подключения.
Пример кода для чтения XLS-файла:
Процедура ПрочитатьДанныеЧерезADO(ПутьКФайлуXLS)
Попытка
Соединение = Новый COMОбъект("ADODB.Connection");
// Строка подключения для старого формата XLS (Excel 97-2003)
// HDR=YES означает, что первая строка на листе - это заголовок колонок
СтрокаПодключения = "Provider=Microsoft.ACE.OLEDB.12.0;"
+ "Data Source=" + ПутьКФайлуXLS + ";"
+ "Extended Properties=""Excel 8.0;HDR=YES"";";
Соединение.Open(СтрокаПодключения);
Исключение
Сообщить("Ошибка подключения через ADO: " + ОписаниеОшибки());
Возврат;
КонецПопытки;
// Имя листа должно быть в квадратных скобках со знаком $ в конце
ТекстЗапроса = "SELECT * FROM [Лист1$]";
НаборЗаписей = Соединение.Execute(ТекстЗапроса);
Пока НЕ НаборЗаписей.EOF() Цикл
// Обращаемся к данным по имени колонки (если HDR=YES) или по индексу
ФИО = НаборЗаписей.Fields("ФИОРаботника").Value;
Количество = НаборЗаписей.Fields("КоличествоОбедов").Value;
// ... ваша логика обработки данных ...
НаборЗаписей.MoveNext();
КонецЦикла;
НаборЗаписей.Close();
Соединение.Close();
Сообщить("Данные успешно прочитаны через ADO.");
КонецПроцедуры
Для чтения XLSX-файла строка подключения будет немного другой, изменится параметр Extended Properties:
"Extended Properties=""Excel 12.0 Xml;HDR=YES"";"
Этот способ очень эффективен для чтения больших объемов структурированных данных.
Если код 1С исполняется на сервере под управлением ОС Linux, COM-объекты недоступны. В этом случае для конвертации можно использовать офисный пакет LibreOffice, который умеет работать из командной строки в "безголовом" режиме (без графического интерфейса).
Из 1С можно запустить внешнюю команду с помощью объекта ЗапуститьПриложение().
Команда для конвертации выглядит так:
libreoffice --convert-to xlsx /путь/к/файлу/my.xls --headless --outdir /путь/к/папке/результата
Этот метод требует, чтобы на сервере был установлен LibreOffice.