Проблеми у використанні FTP-клієнта на базі UTL_TCP


Сьогодні хотілося б розповісти небагато про проблеми у використанні пакету ftp з www.oracle-base.com. Я знаю багатьох, хто його використовує, сам не є винятком. Що сказати, зручно, прям з бази зібрав дані, запхав їх у потрібні таблиці і не потрібно морочитися з окремим зовнішнім складальником. Але в четвер ми наткнулися на проблему, вирішили яку тільки сьогодні (разом 4 робочих дні і 1 вихідний). Отже …

Кому не цікава історія, а потрібен конкретний рада, тупотять до Рішення.

З четверга почали з'являтися сесії, активні по багато годин, вірніше поки не грохнешь, а грохнути через ALTER SYSTEM KILL SESSION не вдавалося, так і висіли зі статусом KILLED. У п'ятницю користувачі почали дзвонити і говорити, що при спробі виконати функцію "Бла-бла-бла" отримують зависле додаток. Ну робити нічого, треба вирішувати швидко, благо користувачів небагато, зробив STARTUP FORCE і начебто все запрацювало. Але це милицю, який використовувати часто не можна, а краще взагалі не користуватися.
Невеликий ліричний відступ … Система побудована для виконання даної функції приблизно так: сервер додатків (IIS) <-> основний інстанси <-> допоміжний <-> маса ftp-серверів. Допоміжний інстанси заведений на сервері, розташованому в двох сітках і використовується виключно для передачі даних між сітками (так уже була придумана секьюрность ще до мого приходу). На допоміжному інстанси використовується вказаний імпровізований ftp-клієнт c Oracle-Base. Написана пара функцій, які повертають вміст необхідних файлів. Доступ до цих функцій виконується через DB Link з основного інстанси.
Так ось, працювало воно працювало, працювало воно працювало, і тут бац! і перестало працювати. Буває. Почали шукати проблему у себе, де може бути зациклення, deadlocks і т.п. (У логах то було ORA-02080). Загалом прийшов до того (відкопав на SQL.RU), що ця помилка видається нам, якщо дуже довго читаються / очікуються дані через лінку. Полізли вручну на FTP, виявилося реально проблема з ftp-сервером. Однак було незрозуміло, чому сесія вішається в статусі ACTIVE, а не відвалюється з таймаут. Обмежували навіть час життя з'єднання в програмі, але все одно сесії на сервері залишалися навіть після того як додаток завершувало свою роботу з таймаут.
Тут як на зло полагодили FTP … Відтворити помилку нереально …
Тут поліз по досі незрозумілою мені причини в пакет ftp, у функцію login і виявив, що при створенні з'єднання в UTL_TCP.OPEN_CONNECTION не передається таймаут. За умовчанням він встановлений в NULL, що означає, що він нескінченний і помилка з таймаут не вивалився ніколи.

Рішення


Ось вирішив я підправити цей пакет для можливості установки таймауту, чого і вам раджу.
У специфікації пакета FTP робимо такі зміни:

FUNCTION login (p_host    IN  VARCHAR2,
p_port IN VARCHAR2,
p_user IN VARCHAR2,
p_pass IN VARCHAR2,
p_timeout IN NUMBER := NULL)
RETURN UTL_TCP.connection;

У тілі пакету робимо так:
FUNCTION login (p_host    IN  VARCHAR2,
p_port IN VARCHAR2,
p_user IN VARCHAR2,
p_pass IN VARCHAR2,
p_timeout IN NUMBER := NULL)
RETURN UTL_TCP.connection IS
– ———————————————— ————————–
l_conn UTL_TCP.connection;
BEGIN
g_reply.delete;

l_conn: = UTL_TCP.open_connection (p_host, p_port, tx_timeout => p_timeout);
get_reply (l_conn);
send_command(l_conn, “USER ” // p_user);
send_command(l_conn, “PASS ” // p_pass);
RETURN l_conn;
END;


Відповідно, у своїх програмах, де потрібно все ж таки встановити таймаут, викликаєте ftp.login із зазначенням p_timeout => 60 (для таймауту = 1 хвилині).
 

Схожі статті:


Сподобалася стаття? Ви можете залишити відгук або підписатися на RSS , щоб автоматично отримувати інформацію про нові статтях.

Коментарів поки що немає.

Ваш отзыв

Поділ на параграфи відбувається автоматично, адреса електронної пошти ніколи не буде опублікований, допустимий HTML: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>

*

*