Как загрузить файл на FTP-сервер из 1С, если возникает ошибка записи?

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

При работе с выгрузкой данных из 1С на FTP-сервер часто возникает задача автоматической отправки файлов. Стандартный объект FTPСоединение предоставляет для этого все необходимые инструменты. Однако иногда, несмотря на успешное подключение к серверу, попытка записать файл завершается неудачей без внятного сообщения об ошибке. Проанализируем типичную ситуацию: соединение устанавливается, но метод Записать() не выполняется, и файл на сервере не появляется. Выясним, в чем может быть причина и как это исправить.

Анализ проблемы: почему не работает запись на FTP?

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


Попытка
    FTPСоединение = Новый FTPСоединение(СерверFTP,ПортFTP,ПользовательFTP,ПарольFTP);
Исключение
    Сообщить("Не удалось установить FTP соединение!");
    Возврат;
КонецПопытки;

FTPСоединение.Записать(ПолныйПутьКФайлу, ИмяФайлаНаСервере);

FTPСоединение = Неопределено;

На первый взгляд, код выглядит корректно. Создается объект FTPСоединение с необходимыми параметрами, а затем вызывается метод Записать(). Проблема в том, что по умолчанию 1С пытается установить активное FTP-соединение. В этом режиме сервер инициирует соединение с клиентом для передачи данных. Большинство современных сетевых инфраструктур, включая брандмауэры и NAT, блокируют такие входящие соединения из соображений безопасности. В результате соединение для передачи данных не устанавливается, и файл не загружается.

Решением является использование пассивного режима FTP. В этом режиме клиент сам инициирует соединение для передачи данных, что, как правило, разрешено сетевыми политиками. В 1С за это отвечает свойство ПассивноеСоединение.

Решение: Использование пассивного режима соединения

Чтобы гарантированно записать файл на сервер, необходимо явно указать 1С использовать пассивный режим. Для этого после создания объекта FTPСоединение и перед вызовом метода Записать() нужно установить свойство ПассивноеСоединение в значение Истина.

Давайте по шагам разберем исправленный и дополненный код.

  1. Устанавливаем соединение

    Сначала создаем новый экземпляр объекта FTPСоединение, передавая ему адрес сервера, порт, логин и пароль. Весь этот блок лучше обернуть в конструкцию Попытка-Исключение, чтобы отловить возможные ошибки подключения (неверный адрес, порт, проблемы с сетью).

    
    // Определяем параметры подключения
    СерверFTP = "ftp.example.com";
    ПортFTP = 21;
    ПользовательFTP = "user";
    ПарольFTP = "password";
    ПолныйПутьКФайлу = "C:\temp\upload.zip";
    ИмяФайлаНаСервере = "upload.zip";
    
    Попытка
        // Создаем объект соединения
        FTPСоединение = Новый FTPСоединение(СерверFTP, ПортFTP, ПользовательFTP, ПарольFTP);
    Исключение
        Сообщить("Не удалось установить FTP соединение! " + ОписаниеОшибки());
        Возврат;
    КонецПопытки;
    
  2. Включаем пассивный режим

    Это ключевой шаг, который решает исходную проблему. Устанавливаем соответствующее свойство в Истина.

    
    // Устанавливаем пассивный режим для обхода брандмауэров
    FTPСоединение.ПассивноеСоединение = Истина;
    
  3. Записываем файл на сервер

    Теперь вызываем метод Записать(). Он принимает два параметра: первый — это полный путь к файлу на локальном компьютере, который нужно загрузить, а второй — имя, под которым файл будет сохранен на FTP-сервере. Эту операцию также стоит обернуть в Попытка-Исключение, чтобы обработать возможные ошибки, связанные с правами доступа на запись в целевой каталог или нехваткой места на сервере.

    
    Попытка
        FTPСоединение.Записать(ПолныйПутьКФайлу, ИмяФайлаНаСервере);
        Сообщить("Файл успешно загружен на FTP-сервер.");
    Исключение
        Сообщить("Ошибка при записи файла на FTP: " + ОписаниеОшибки());
    КонецПопытки;
    
  4. Завершаем работу

    После выполнения всех операций важно освободить ресурсы, присвоив переменной FTPСоединение значение Неопределено. Это закроет соединение с сервером.

    
    FTPСоединение = Неопределено;
    

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

Для более надежной работы рекомендуется также проверять существование каталога на FTP-сервере и создавать его при необходимости. Это можно сделать с помощью метода СоздатьКаталог().

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


Процедура ВыгрузитьФайлНаFTP()
    
    // Параметры
    СерверFTP = "ftp.example.com";
    ПортFTP = 21;
    ПользовательFTP = "user";
    ПарольFTP = "password";
    ЛокальныйФайл = "C:\temp\data.xml";
    УдаленныйПуть = "/uploads/data.xml";

    // Инициализация переменной
    FTPСоединение = Неопределено;

    // Основной блок работы с FTP
    Попытка
        // 1. Установка соединения
        FTPСоединение = Новый FTPСоединение(СерверFTP, ПортFTP, ПользовательFTP, ПарольFTP, , , Истина); // Последний параметр - таймаут
        
        // 2. Включение пассивного режима (важнейший шаг)
        FTPСоединение.ПассивноеСоединение = Истина;
        
        // 3. (Опционально) Проверка и создание каталога на сервере
        // Например, если нужно положить файл в папку /uploads
        // В данном примере мы этого не делаем, но можно раскомментировать
        // Попытка
        //     FTPСоединение.УстановитьТекущийКаталог("/uploads");
        // Исключение
        //     // Если каталога нет, создаем его
        //     FTPСоединение.СоздатьКаталог("/uploads");
        // КонецПопытки;

        // 4. Запись файла
        FTPСоединение.Записать(ЛокальныйФайл, УдаленныйПуть);
        
        Сообщить("Файл '" + ЛокальныйФайл + "' успешно выгружен в '" + УдаленныйПуть + "'");

    Исключение
        Сообщить("Произошла ошибка при работе с FTP: " + ОписаниеОшибки());
    КонецПопытки;
    
    // 5. Закрытие соединения
    Если FTPСоединение <> Неопределено Тогда
        FTPСоединение = Неопределено;
    КонецЕсли;

КонецПроцедуры

Таким образом, основная причина неудачной записи файла на FTP-сервер при рабочем подключении — это блокировка активного режима соединения. Простое добавление строки FTPСоединение.ПассивноеСоединение = Истина; перед вызовом метода записи решает эту проблему в большинстве случаев, обеспечивая стабильную и надежную выгрузку файлов из 1С.

← На главную