Время ожидания соединения при idSMTP при использовании TIdSSLIOHandlerSocketOpenSSL

#delphi #delphi-xe #indy10

#delphi #delphi-xe #indy10

Вопрос:

У меня возникла проблема с использованием TIdSMTP, когда TIdSSLIOHandlerSocketOpenSSL получает «Ошибку сокета» просто при подключении к серверу.

Вот код компонента формы

   object IdSMTP: TIdSMTP
    IOHandler = IdSSLIOHandlerSSL
    Port = 465
    SASLMechanisms = <>
    UseTLS = utUseImplicitTLS
    Left = 93
    Top = 49
  end
  object IdSSLIOHandlerSSL: TIdSSLIOHandlerSocketOpenSSL
    OnStatus = IdSSLIOHandlerSSLStatus
    Destination = ':465'
    MaxLineAction = maException
    Port = 465
    DefaultPort = 0
    SSLOptions.Mode = sslmUnassigned
    SSLOptions.VerifyMode = []
    SSLOptions.VerifyDepth = 0
    OnStatusInfo = IdSSLIOHandlerSSLStatusInfo
    Left = 88
    Top = 112
  end
  

и код Delphi

  IdSMTP.Username  := 'username';
 IdSMTP.Password  := 'password';
 IdSMTP.Host      := 'domain';
 IdSMTP.Port      := 465;
 IdSMTP.UseTLS    := utUseImplicitTLS;
 try
    IdSMTP.Connect;
 except
    on E:Exception do
       // Socket Error, Connection Timeout is thrown.
       Memo1.Lines.Add(E.Message);
 end;
  

Я зарегистрировал статус ввода-вывода SSL и получил это:

 Resolving hostname {domain}.
Connecting to {ip}.
SSL status: "before/connect initialization"
SSL status: "before/connect initialization"
SSL status: "SSLv3 write client hello A"
SSL status: "SSLv3 read server hello A"
Socket Error # 10060
Connection timed out.
  

Кстати, наш почтовый сервер использует самозаверяющий сертификат.

Что я делаю не так?

TIA

ОБНОВЛЕНИЕ: 07-02-2014

Пытался отправлять почту в Gmail с помощью подсказки Indy, но я получаю, что соединение закрыто корректно, отправляя электронное письмо также после того, как SSLv3 прочитал сервер hello A.

 Resolving hostname smtp.gmail.com.
Connecting to 74.125.25.108.
Connected.
Sending Email..
SSL status: "before/connect initialization"
SSL status: "before/connect initialization"
SSL status: "SSLv3 write client hello A"
SSL status: "SSLv3 read server hello A"
Disconnected.
Connection Closed Gracefully.
  

Вот новый код:

  IdSMTP.Username  := 'username';
 IdSMTP.Password  := 'password';
 IdSMTP.Host      := 'smtp.gmail.com';
 IdSMTP.UseTLS    := utUseExplicitTLS;
 IdSMTP.Port      := 587;
 try
    // Can connect successfully
    IdSMTP.Connect;

    // This part throws the exception
    IdSMTP.Send(IdMessage);
 except
    on E:Exception do
       // Disconnected, connection closed gracefully 
       Memo1.Lines.Add(E.Message);
 end;
  

Обновить:

Пробовал отправлять электронную почту с помощью Thunderbird, подключаясь к тому же домену.

Thunderbird: Захват Wireshark - отправка электронной почты с помощью thunderbird

Indy: Захват Wireshark - с использованием Indy

В моей программе не произошло «обмена ключами клиента, …«.

РЕШАЕМАЯ

Эта проблема была решена путем ручной настройки connectiontimeout

Ответ №1:

Вы используете неявный SSL. Это означает, что SSL-квитирование инициируется, как только сокет подключен к серверу, до обмена любыми данными приложения (командами / ответами SMTP). На сервер отправляется клиентское приветствие, а затем наступает тайм-аут в ожидании, пока сервер отправит ответное приветствие. Это означает, что сервер НЕ использует SSL на порту, к которому вы подключаетесь.

Что следует иметь в виду — установка UseTLS свойства может изменить Port свойство, поэтому убедитесь, что Port это действительно то, что вы ожидаете при Connect() вызове. Чтобы убедиться, попробуйте установить Port после установки UseTLS , а не до.

Комментарии:

1. ошибка тайм-аута / сокета возникает сразу после приветствия сервера, без дополнительной задержки. соединение внезапно прерывается.

2. порт использует SSL, потому что мы можем отправлять электронную почту с помощью других почтовых клиентов, таких как Thunderbird. Назначение порта после установки UseTLS также приводит к тому же результату.

3. Немедленное отключение, вероятно, означает, что Gmail отклоняет рукопожатие. Вы пробовали использовать анализатор пакетов для просмотра сообщений о квитировании? Кроме того, при подключении к Gmail вы установили SSLVersion значение TLSv1? Не используйте SSLv3.

4. я использую только v1. Прослушал с помощью wireshark и обнаружил, что обмен ключами клиента не происходит при использовании Indy (мы используем самозаверяющий сертификат). Я посмотрю, как я могу обмениваться ключами с нашим сервером.

5. Ваш клиент закрывает сокет (отправляя FIN TCP-пакет) после получения приветствия сервера. Либо OpenSSL отклоняет сертификат сервера, либо возникает исключение, или тому подобное.

Ответ №2:

Пожалуйста, убедитесь, что ваш брандмауэр временно отключен. Я попал на эту страницу, потому что у меня была та же проблема — немедленное отключение с надписью «Соединение закрыто корректно» при выполнении SMTP с SSL. Затем я отключил свой Avast! брандмауэр, и все было в порядке.