Разработка и Конфигурация · 9 мин
Как создать временный файл в 1С
Как создать временный файл в 1С: функция ПолучитьИмяВременногоФайла, работа с текстом и двоичными данными, удаление файлов, типичные ошибки и примеры кода.
Временные файлы в 1С нужны при обмене данными с внешними системами, выгрузке отчётов, формировании печатных форм и передаче файлов между сервером и клиентом. Платформа предоставляет встроенный механизм, который сам выбирает каталог временных файлов операционной системы и генерирует уникальное имя, поэтому разработчику не нужно заботиться о коллизиях имён.
Основной инструмент — функция ПолучитьИмяВременногоФайла() (в английском синтаксисе — GetTempFileName()). Она не создаёт файл сама по себе, а возвращает гарантированно уникальный путь, по которому затем записываются данные. За запись отвечают объекты ТекстовыйДокумент, ЗаписьТекста, ДвоичныеДанные и другие.
Важно понимать: платформа не удаляет временные файлы автоматически. Если код не освобождает их явно, каталог временных файлов сервера или клиента постепенно заполняется мусором, что на загруженных системах приводит к переполнению диска. Поэтому создание временного файла всегда должно сопровождаться его удалением после использования.
Функция ПолучитьИмяВременногоФайла: синтаксис и принцип работы
Функция вызывается с одним необязательным параметром — расширением файла без точки. Если параметр не указан, платформа подставляет расширение по умолчанию (обычно tmp). Возвращаемое значение — строка с полным путём к файлу в системном каталоге временных файлов.
ИмяФайла = ПолучитьИмяВременногоФайла("xml");
// Результат: C:\Users\User\AppData\Local\Temp\1cv8.tmp\...
// или на Linux: /tmp/...
Ключевая особенность: функция не записывает ничего на диск. Она лишь резервирует уникальное имя. Физически файл появится только после вызова метода записи. Это удобно, когда путь нужно передать в сторонний механизм — например, сохранение табличного документа или выгрузку через COM-объект.
Создание текстового временного файла
Самый частый сценарий — сформировать текстовый файл (CSV, XML, JSON, лог) и передать его дальше. Для этого используются два объекта: ТекстовыйДокумент для простых случаев и ЗаписьТекста, когда нужен контроль над кодировкой и разделителями строк.
ИмяФайла = ПолучитьИмяВременногоФайла("csv");
Текст = Новый ТекстовыйДокумент;
Текст.ДобавитьСтроку("Номенклатура;Количество;Цена");
Текст.ДобавитьСтроку("Кабель ВВГ;10;150");
Текст.Записать(ИмяФайла, КодировкаТекста.UTF8);
Вариант с ЗаписьТекста предпочтителен при потоковой записи больших объёмов данных, так как не держит весь документ в памяти:
Запись = Новый ЗаписьТекста(ИмяФайла, КодировкаТекста.UTF8);
Запись.ЗаписатьСтроку("первая строка");
Запись.Закрыть();
Обязательно вызывайте Закрыть() у ЗаписьТекста — пока поток открыт, файл заблокирован, и другие механизмы (например, отправка по HTTP или чтение клиентом) получат ошибку доступа.
Работа с двоичными данными и табличными документами
Когда нужно сохранить картинку, архив или произвольный набор байт, используется тип ДвоичныеДанные. Часто данные приходят из хранилища значения, HTTP-ответа или макета конфигурации.
ДанныеКартинки = Справочники.Файлы.НайтиПоКоду("0001").Данные.Получить();
ИмяФайла = ПолучитьИмяВременногоФайла("png");
ДанныеКартинки.Записать(ИмяФайла);
Табличный документ сохраняется во временный файл напрямую методом Записать() с указанием типа файла. Так формируют, например, Excel-файлы для выгрузки прайсов:
ИмяФайла = ПолучитьИмяВременногоФайла("xlsx");
ТабДокумент.Записать(ИмяФайла, ТипФайлаТабличногоДокумента.XLSX);
Передача файла с сервера на клиент
В клиент-серверном режиме временный файл, созданный в серверном коде, физически находится на сервере — клиент его не увидит. Для передачи используется механизм временного хранилища: файл помещается туда через ПоместитьВоВременноеХранилище(), а на клиенте извлекается и сохраняется.
// Серверная процедура
ИмяФайла = ПолучитьИмяВременногоФайла("xlsx");
ТабДокумент.Записать(ИмяФайла, ТипФайлаТабличногоДокумента.XLSX);
Адрес = ПоместитьВоВременноеХранилище(Новый ДвоичныеДанные(ИмяФайла), ИдентификаторФормы);
УдалитьФайлы(ИмяФайла);
// Клиентская процедура
ПолучитьФайл(Адрес, "Прайс.xlsx", Истина);
Обратите внимание: после помещения данных в хранилище серверный временный файл уже не нужен и удаляется сразу. Адрес хранилища привязывается к форме через её уникальный идентификатор — тогда данные живут, пока открыта форма, и не висят в памяти сервера бесконечно.
- 1Вызовите ПолучитьИмяВременногоФайла() с нужным расширением
- 2Запишите данные подходящим объектом (ТекстовыйДокумент, ЗаписьТекста, ДвоичныеДанные)
- 3Закройте потоки записи, если они использовались
- 4Передайте файл потребителю или поместите во временное хранилище
- 5Удалите файл через УдалитьФайлы() в блоке Исключение-обработки
Удаление временных файлов и защита от утечек
Удаление выполняется процедурой УдалитьФайлы(Путь). Правильный шаблон — оборачивать работу с файлом в попытку, а удаление выносить так, чтобы оно сработало даже при ошибке:
ИмяФайла = ПолучитьИмяВременногоФайла("xml");
Попытка
// ... запись и использование файла
Исключение
// логирование ошибки
КонецПопытки;
Если НайтиФайлы(ИмяФайла).Количество() > 0 Тогда
УдалитьФайлы(ИмяФайла);
КонецЕсли;
Если файл всё ещё занят открытым потоком, УдалитьФайлы вызовет исключение. Поэтому сначала закрывайте все объекты записи и чтения. На сервере 1С каталог временных файлов стоит периодически очищать регламентными средствами ОС — это страховка от утечек в старом коде.
Типичные ошибки и их последствия
Практика сопровождения показывает, что большинство проблем с временными файлами связано не с их созданием, а с жизненным циклом и доступом. Ниже — ошибки, которые встречаются чаще всего.
Отдельного внимания заслуживает параллельность. Именно поэтому нельзя подменять ПолучитьИмяВременногоФайла самодельной генерацией имён: встроенная функция гарантирует уникальность в пределах системы, а самописная схема — нет.
Проверка результата и FAQ
После записи файла полезно убедиться, что он реально существует и не пуст. Для этого используются НайтиФайлы() и объект Файл с проверкой размера:
Файл = Новый Файл(ИмяФайла);
Если Файл.Существует() И Файл.Размер() > 0 Тогда
// файл готов к использованию
КонецЕсли;
Как проверить результат
Файл.Существует() возвращает Истина
Файла нет — запись не выполнялась или путь неверен
Размер больше нуля и соответствует объёму данных
Нулевой размер — поток записи не был закрыт
Файл открывается без ошибки доступа
Ошибка доступа — файл занят открытым потоком
Количество файлов стабильно во времени
Каталог растёт — в коде есть утечки временных файлов
Что важно запомнить
ПолучитьИмяВременногоФайла() даёт уникальный путь, запись выполняют ТекстовыйДокумент, ЗаписьТекста или ДвоичныеДанные, передача клиенту идёт через временное хранилище, а удаление через УдалитьФайлы() — обязательная завершающая операция.
Создаёт ли ПолучитьИмяВременногоФайла сам файл на диске?
Нет. Функция только генерирует уникальный путь в каталоге временных файлов. Физически файл появляется после вызова метода записи — например, ТекстовыйДокумент.Записать() или ДвоичныеДанные.Записать().
Удаляет ли платформа временные файлы автоматически?
Нет, автоматической очистки со стороны платформы нет. Файл нужно удалять явно через УдалитьФайлы() после использования. Иначе каталог TEMP на сервере постепенно переполняется, что приводит к сбоям серверных вызовов.
Почему клиент не видит временный файл, созданный на сервере?
Потому что файл физически лежит на диске сервера 1С. Для передачи клиенту данные помещают во временное хранилище через ПоместитьВоВременноеХранилище(), а на клиенте извлекают по полученному адресу и сохраняют локально.
Какое расширение указывать, если формат неважен?
Можно вызвать функцию без параметра — будет подставлено расширение по умолчанию (как правило, tmp). Однако если файл потом открывается внешней программой, лучше указать осмысленное расширение (txt, xml, xlsx), чтобы приложение корректно ассоциировало тип.
Что делать, если УдалитьФайлы выдаёт ошибку доступа?
Ошибка означает, что файл занят открытым потоком. Проверьте, что все объекты ЗаписьТекста и ЧтениеТекста закрыты методом Закрыть(), а внешние программы не держат файл. После закрытия потоков удаление выполняется успешно.
Можно ли задать собственный каталог вместо системного TEMP?
Напрямую через ПолучитьИмяВременногоФайла — нет, функция всегда использует системный каталог. Если нужен свой каталог, формируйте путь вручную (например, КаталогВременныхФайлов() + подкаталог), но тогда уникальность имён и очистку придётся обеспечивать самостоятельно.