Возникает задача, когда необходимо массово обновить большое количество уже существующих документов Word, добавив в них определенный блок текста. Сложность в том, что документы уже созданы, и в них нет заранее подготовленных закладок или специальных меток-плейсхолдеров для вставки. Требуется вставить текст в визуально одно и то же место на странице, например, в определенный угол или под определенным абзацем.
Проанализируем ситуацию и разберем несколько способов решения этой задачи как средствами платформы 1С, так и с помощью внешних инструментов, таких как Python.
Это классический и наиболее гибкий способ взаимодействия с приложениями Microsoft Office из 1С. Он требует, чтобы MS Word был установлен на том компьютере, где будет выполняться код (на клиенте или на сервере). Этот метод позволяет имитировать практически любые действия пользователя.
Вариант А: Вставка по точным координатам с помощью объекта Shape (TextBox)
Этот способ идеально подходит для задачи "вставить текст в визуально определенное место". Идея заключается в том, чтобы не просто вставить текст в поток документа, а создать поверх страницы объект "Надпись" (TextBox) с точными координатами и поместить наш текст внутрь него.
Самый простой способ получить нужный код — это записать макрос в самом Word, а затем адаптировать его для 1С. Разберем по шагам:
Примерный код на 1С, адаптированный из VBA-макроса, может выглядеть так:
Попытка
WordApp = Новый COMОбъект("Word.Application");
Исключение
Сообщить("Не удалось запустить MS Word. Проверьте, установлена ли программа.");
Возврат;
КонецПопытки;
WordApp.Visible = Истина; // Устанавливаем в Ложь для фоновой работы
// Путь к вашему файлу
ПутьКФайлу = "C:\МоиДокументы\Договор_123.docx";
Документ = WordApp.Documents.Open(ПутьКФайлу);
// Координаты (в пунктах) и размеры надписи.
// Эти значения вы получите из записанного макроса.
Лево = 400;
Верх = 100;
Ширина = 150;
Высота = 50;
ТекстДляВставки = "Текст, который нужно вставить в документ.";
// Добавляем объект TextBox (надпись)
// ActiveDocument.Shapes.AddTextbox(Orientation, Left, Top, Width, Height)
Надпись = Документ.Shapes.AddTextbox(1, Лево, Верх, Ширина, Высота);
// Вставляем текст и убираем рамку
Надпись.TextFrame.TextRange.Text = ТекстДляВставки;
Надпись.Line.Visible = 0; // 0 = False, рамка невидима
Документ.Save();
Документ.Close();
WordApp.Quit();
Важно: Координаты и размеры задаются в пунктах (points), а не в пикселях или сантиметрах. Запись макроса поможет вам точно определить нужные значения для вашего случая.
Вариант Б: Поиск и замена текста
Если в документах есть какой-то уникальный текст-"якорь", рядом с которым нужно произвести вставку, можно использовать встроенный механизм поиска и замены. Этот метод более надежен, чем вставка по координатам, так как он не зависит от полей, форматирования и других плавающих элементов.
// ... код подключения к Word ...
Документ = WordApp.Documents.Open(ПутьКФайлу);
// Получаем объект для поиска по всему документу
Выделение = WordApp.Selection;
Поиск = Выделение.Find;
Поиск.ClearFormatting(); // Очищаем предыдущие параметры поиска
ТекстКоторыйИщем = "Приложение №1";
ТекстКоторыйВставляем = "Приложение №1 (утверждено)";
// Указываем, что нужно искать
Поиск.Text = ТекстКоторыйИщем;
// Параметры замены
Замена = Поиск.Replacement;
Замена.ClearFormatting();
Замена.Text = ТекстКоторыйВставляем;
// Выполняем замену всех вхождений в документе
// wdReplaceAll = 2
Поиск.Execute( , , , , , , , , , , 2);
Документ.Save();
// ... код закрытия Word ...
Современные файлы формата .docx — это, по сути, ZIP-архивы, внутри которых находятся XML-файлы, описывающие структуру и содержимое документа. Это позволяет работать с ними на сервере 1С под Linux или в любом окружении, где нет установленного MS Office.
Внимание: этот способ требует глубокого понимания структуры OpenXML и является более сложным в реализации.
Алгоритм действий следующий:
ЧтениеZipФайла или внешних утилит необходимо распаковать .docx файл во временный каталог.word/document.xml. Необходимо прочитать этот XML-файл, найти нужный узел (например, определенный параграф <w:p>) и добавить в него новые узлы с текстом <w:r><w:t>Ваш текст</w:t></w:r>. Для работы с XML в 1С используются объекты ЧтениеXML и ПостроительDOM.ЗаписьZipФайла и присвоить ему расширение .docx.Этот подход является самым производительным и кроссплатформенным, но и самым трудоемким. Он оправдан в высоконагруженных системах или при работе на серверах без графической оболочки.
Если задача разовая и требует быстрой автоматизации для сотен файлов, Python может быть отличным выбором. Для работы с Word-документами существуют мощные библиотеки.
Основная библиотека: python-docx. Она позволяет читать и изменять содержимое документа на уровне параграфов, таблиц, стилей.
Посмотрим на пример кода, который ищет во всех файлах в папке определенную строку и заменяет ее на новую. Это может решить задачу, если у вас есть текст-"якорь".
# Сначала нужно установить библиотеку: pip install python-docx
import glob
import pathlib
from docx import Document
# Указываем папки
in_dir = "c:\\temp\\docs\\" #ГДЕ ЛЕЖАТ ФАЙЛЫ
out_dir = "c:\\temp\\docs\\out\\" #КУДА СОХРАНИТЬ ИЗМЕНЕННЫЕ ФАЙЛЫ
# Создаем выходную папку, если ее нет
pathlib.Path(out_dir).mkdir(parents=True, exist_ok=True)
# Строки для поиска и замены
oldstr = "Не допускайте к работе"
newstr = "ДОПУСКАЙТЕ К РАБОТЕ СТРОГО ПОСЛЕ ИНСТРУКТАЖА"
# Получаем список всех .docx файлов в папке
filelist = glob.glob(in_dir + '*.docx')
# Перебираем файлы в цикле
for f in filelist:
print(f"Обработка файла: {f}")
doc = Document(f)
# Перебираем все параграфы в документе
for p in doc.paragraphs:
# Проверяем, есть ли искомый текст в параграфе
if oldstr in p.text:
# Заменяем текст. ВАЖНО: это заменяет весь текст параграфа
# Для сохранения форматирования нужны более сложные манипуляции с объектами Run
p.text = p.text.replace(oldstr, newstr)
# Сохраняем измененный документ в другую папку
ff = out_dir + pathlib.Path(f).name
doc.save(ff)
print(f"Файл сохранен как: {ff}")
print("Обработка завершена.")
Этот скрипт можно легко адаптировать под свои нужды. Он не требует установленного MS Word и работает очень быстро.
Чтобы в будущем не сталкиваться с необходимостью "хирургического" вмешательства в готовые документы, рекомендуем придерживаться следующих практик при их генерации:
[НомерДоговора] или %%ФИОКлиента%%. Затем, при формировании документа, можно программно выполнить поиск и замену этих меток на реальные данные. Этот подход также хорошо работает со встроенными в конфигурации (например, 1С:Документооборот) механизмами автозаполнения шаблонов.Эти подходы делают процесс генерации документов предсказуемым, управляемым и легко модифицируемым.