【问题标题】:TIdTCPClient: Reconnect implementationTIdTCPClient:重新连接实现
【发布时间】:2012-11-04 02:13:27
【问题描述】:

我正在编写一个应用程序,它使用TIdTCPClient 通过套接字与另一个应用程序通信。

我希望应用程序尝试连接到某个服务器,直到建立连接(即,直到服务器上线)。

为了做到这一点,我编写了以下代码:

procedure SendingThread.Execute();
var
I : integer;
Test : string;
IsConnected : Boolean;
begin
    TcpClient := TIdTCPClient.Create;
    TcpClient.Host := '127.0.0.1';
    TcpClient.Port := 9999;
    TcpClient.ConnectTimeout := 60000;

    IsConnected := false;
    while not IsConnected do
        begin
        try
            TcpClient.Connect;
            IsConnected := True;
        except
            on E:EIdSocketError do
                IsConnected := false;
        end;
    end;
...
end;

当我在服务器脱机的情况下运行此代码时,我得到EIdSocketError 错误代码10061。在TcpClient.Connect;之后抛出异常。

如何修改代码,以便在except 原因中捕获此异常?

【问题讨论】:

  • TIdTCPClient.Connect 是同步的,所以你发布的代码很好,除了你应该修改你的循环以检查Terminatedwhile not Terminated and not IsConnected do 这样的线程的标志,除了你可以进入无限连接尝试循环。但是在调用TcpClient.Connect; 后无法到达IsConnected := True; 行,连接失败。
  • 将条件更改为while (not IsConnected) and (not Terminated) do 并不能修复错误(尝试过)。
  • 我知道,这只是建议您应该如何修改该循环 :-) 我看不到任何 错误。你调试过这段代码吗?我敢打赌,如果您尝试连接到不存在的服务器,那么您将永远无法到达在 IsConnected := True; 行(使用当前代码)设置的断点。
  • 是的,我正在调试器中运行代码。问题是如何以编程方式检测服务器不可用。
  • 不,此时的问题是我怎样才能修改代码,以便在except子句中捕获异常?答案是什么Don '不要修改代码,连接尝试异常已经被捕获.

标签: delphi delphi-2009 indy


【解决方案1】:

这里不需要while循环,因为你已经在一个线程中执行,这个while循环只会执行一次,如果没有连接,你的线程将处于无限循环中。

【讨论】:

    【解决方案2】:

    无需修改代码。*您的程序已经捕捉到预期的异常。

    您所看到的是调试器在异常被抛出后立即拦截,在您的程序有机会看到异常存在并对其执行任何操作之前。当 IDE 中断您时,它会显示一个对话框,让您可以选择继续运行。执行该选项,或在关闭对话框后按“运行”按钮。

    您可以将调试器配置为忽略部分或全部异常,这在使用 Indy 时特别有用,Indy 倾向于使用异常进行正常的流控制。 How to do that has been covered here before.

    * Remy 的回答描述了您可以对代码进行的改进以捕获其他可能的异常。

    【讨论】:

      【解决方案3】:

      您展示的代码是处理重新连接问题的正确方法,但您需要对其进行一点小改动。将except 块更改为捕获ExceptionEIdException 而不是EIdSocketErrorEIdSocketError 不是Connect() 可以引发的唯一可能的异常。例如,它可以引发EIdConnectExceptionEIdConnectTimeout,它们都不是从EIdSocketError 派生的。

      procedure SendingThread.Execute;
      var
        ...
        IsConnected : Boolean;
      begin
        ...
        IsConnected := False;
        while (not IsConnected) and (not Terminated) do
        begin
          try
            TcpClient.Connect;
            IsConnected := True;
          except
            on E: Exception do
              IsConnected := False;
          end;
        end;
        ...
      end;
      

      您也可以完全删除on E 子句,因为它没有做任何有用的事情。引发异常时,IsConnected 变量已经为 False,因此无需将其重新分配给相同的值。

      procedure SendingThread.Execute;
      var
        ...
        IsConnected : Boolean;
      begin
        ...
        IsConnected := false;
        while (not IsConnected) and (not Terminated) do
        begin
          try
            TcpClient.Connect;
            IsConnected := True;
          except
          end;
        end;
        ...
      end;
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2017-05-09
        • 1970-01-01
        • 2016-02-17
        • 1970-01-01
        • 1970-01-01
        • 2019-02-16
        • 2019-07-17
        • 2011-06-27
        相关资源
        最近更新 更多