Почему 1С зависает или вылетает при чтении файлов Excel через ТабДок.Прочитать() и как это исправить?

Программист 1С v8.3 (Управляемые формы) IT и автоматизация бизнеса
← На главную

Работа с внешними данными в формате Excel — одна из самых частых задач для разработчика 1С. Казалось бы, штатный механизм ТабличныйДокумент.Прочитать() должен работать безупречно, однако на практике многие сталкиваются с критической ошибкой: программа просто «умирает» или бесконечно «висит» при попытке загрузить очередной файл. При этом стандартные блоки Попытка...Исключение не срабатывают, так как проблема происходит на уровне ядра системы.

В этой статье мы подробно разберем, почему возникают такие ситуации, проанализируем внутренние механизмы платформы и выясним, как обойти эти ограничения, чтобы ваша загрузка данных работала стабильно.

Причина зависания: заглядываем внутрь moxel.dll

Для начала проанализируем ситуацию: когда мы вызываем метод Прочитать(), платформа 1С задействует внутреннюю библиотеку moxel.dll. Эта библиотека отвечает за работу с табличными документами и содержит парсер формата OpenXML (xlsx). Проблема заключается в том, что 1С пытается не просто прочитать данные из ячеек, а полностью реконструировать структуру документа со всеми его визуальными элементами.

Рассмотрим основные технические причины, по которым парсер может уйти в бесконечный цикл или вызвать ошибку доступа к памяти (Access Violation):

  1. Сложные графические объекты (Drawing objects): Кнопки, формы обратной связи, элементы ActiveX и даже обычные автофигуры могут стать причиной сбоя. Если объект привязан к ячейке некорректно или имеет «нулевые» координаты, парсер 1С при расчете сетки документа может войти в рекурсию.
  2. Форматирование примечаний: Как было выяснено в ходе обсуждения, даже такая мелочь, как цвет линий в примечании (например, темно-синий вместо стандартного), может привести к краху moxel.dll. 1С очень чувствительна к нестандартным стилям в XML-структуре файла.
  3. Защита листов и макросы: Наличие защиты листа в сочетании с элементами управления часто блокирует нормальный доступ парсера к метаданным документа.
  4. Несоответствие расширения и структуры: Если файл имеет расширение .xlsm (с макросами), а вы просто переименовали его в .xlsx, внутренняя структура файла не изменится. В нем останутся части vbaProject.bin, на которые могут ссылаться кнопки или другие объекты. 1С пытается найти эти связи, не находит и зависает.

Метод 1: Очистка файла в самом Excel

Если зависание происходит на конкретном файле, первым делом стоит проверить его содержимое вручную. Рассмотрим, на что нужно обратить внимание:

Во-первых, проверим наличие скрытых графических объектов. В Excel перейдите на вкладку «Главная», выберите «Найти и выделить», затем «Выбор объектов». Попробуйте выделить область листа — часто там обнаруживаются невидимые «мусорные» кнопки или пустые рамки, оставшиеся от старых макросов. Удалите их.

Во-вторых, обратите внимание на примечания. Попробуйте сбросить форматирование всех примечаний к стандартному. Как показывает практика, установка черного цвета линий и стандартного шрифта часто решает проблему зависания 1С.

В-третьих, если файл содержит макросы, его нужно не переименовывать, а пересохранять через «Сохранить как» в формат «Книга Excel (.xlsx)». Это полностью пересоберет XML-структуру и удалит ссылки на VBA-проект.

Метод 2: Программная подготовка файла через COM-объект

Если файлов много и очищать их вручную невозможно, мы можем использовать Microsoft Excel как промежуточное звено для «лечения» файла перед тем, как его прочитает 1С. Суть метода заключается в том, чтобы открыть файл через COM и пересохранить его. Excel при сохранении сам исправит мелкие ошибки в структуре XML.

Рассмотрим пример кода для такой предварительной обработки:


Функция ПодготовитьФайлКЗагрузке(ПутьКФайлу)
    
    Попытка
        Excel = Новый COMОбъект("Excel.Application");
    Исключение
        Возврат ПутьКФайлу; // Если Excel не установлен, возвращаем как есть
    КонецПопытки;
    
    Excel.DisplayAlerts = Ложь;
    Excel.Visible = Ложь;
    
    Попытка
        Книга = Excel.Workbooks.Open(ПутьКФайлу);
        
        // Удаляем все фигуры и кнопки на всех листах, если они не нужны для данных
        Для Каждого Лист Из Книга.Sheets Цикл
            Для НомерФормы = 1 По Лист.Shapes.Count Цикл
                Лист.Shapes.Item(1).Delete();
            КонецЦикла;
        КонецЦикла;
        
        НовыйПуть = ПолучитьИмяВременногоФайла("xlsx");
        // Параметр 51 соответствует формату xlsx без макросов
        Книга.SaveAs(НовыйПуть, 51);
        Книга.Close();
        
        Возврат НовыйПуть;
    Исключение
        Сообщить("Ошибка при обработке файла через COM: " + ОписаниеОшибки());
        Возврат ПутьКФайлу;
    КонецПопытки;
    
    Excel.Quit();
    
КонецФункции

После такой обработки файл становится «чистым» для парсера 1С, и метод ТабДок.Прочитать(НовыйПуть) отработает мгновенно.

Метод 3: Использование альтернативных способов чтения (ADO/ACE)

Если вам нужно прочитать только данные (строки и колонки), а оформление, цвета и примечания вас не интересуют, проанализируем возможность использования технологии ADO (ActiveX Data Objects). Этот метод вообще не использует moxel.dll и ТабличныйДокумент, поэтому он неуязвим к графическим объектам внутри Excel.

Разберем пример подключения к файлу как к базе данных:


Connection = Новый COMОбъект("ADODB.Connection");
ConnectionString = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" + ПутьКФайлу + ";Extended Properties=""Excel 12.0 Xml;HDR=YES"";";

Попытка
    Connection.Open(ConnectionString);
    Recordset = Connection.Execute("SELECT * FROM [Лист1$]");
    
    Пока НЕ Recordset.EOF Цикл
        // Обработка данных
        Значение = Recordset.Fields.Item(0).Value;
        Recordset.MoveNext();
    КонецЦикла;
    
    Recordset.Close();
    Connection.Close();
Исключение
    Сообщить("Ошибка чтения через ADO: " + ОписаниеОшибки());
КонецПопытки;

Использование этого метода гарантирует, что 1С не зависнет из-за кнопки на листе или синего цвета примечания, так как драйвер Microsoft.ACE.OLEDB игнорирует всё, что не является данными в ячейках. При необходимости читать данные напрямую из структуры книги без использования офисного пакета и сторонних драйверов можно применить решение для чтения файлов Excel без MS Office и внешних библиотек.

Дополнительные рекомендации

Проанализируем еще несколько факторов, которые могут влиять на стабильность процесса:

Подводя итог, можно сказать: если вы столкнулись с «мистическим» зависанием, не ищите ошибку в своем коде 1С. Скорее всего, дело в графическом мусоре внутри Excel-файла. Используйте программную очистку через COM или переходите на чтение через ADO, чтобы обеспечить бесперебойную работу ваших интеграций. Для быстрого получения данных всех страниц книги в таблицу значений без ручной настройки парсинга можно применить обработку для универсальной загрузки файлов Excel и CSV.

← На главную