如何使用异步 TNetHTTPClient

How to use asynchronous TNetHTTPClient

如何使用异步TNetHTTPClient? 我尝试了以下代码,但它显示错误。

procedure TForm1.Button1Click(Sender: TObject);
var
  httpclient: TNetHTTPClient;
  output: string;
begin
  httpclient := TNetHTTPClient.Create(nil);
  try
      httpclient.Asynchronous := True;
      output := httpclient.Get('https://google.com').ContentAsString;
  finally
    httpclient.Free;
  end;
end;

错误:

Error querying headers: The handle is in a wrong state for the requested operation

异步模式,顾名思义,客户端运行s在后台线程中异步请求。

执行以下代码时,ContentAsString 失败,因为此时请求尚未完成。

output := httpclient.Get('https://google.com').ContentAsString

如果您想在异步模式下使用 HTTP 客户端,则必须在请求完成后使用完成处理程序 运行 适当的代码。

procedure TForm1.Button1Click(Sender: TObject);
var
  httpclient: TNetHTTPClient;
begin
  httpclient := TNetHTTPClient.Create(nil);
  httpclient.Asynchronous := True;
  httpclient.OnRequestCompleted := HTTPRequestCompleted;
  httpclient.Get('https://google.com');
end;

procedure TForm1.HTTPRequestCompleted(const Sender: TObject; const AResponse: IHTTPResponse);
var
  output: string;
begin
  output := AResponse.ContentAsString;
  Sender.Free;
end;

在异步模式下使用 HTTP 客户端通常比在后台线程中在同步模式下使用更复杂(尤其是从内存管理方面)。

以下是使用匿名后台线程的等效示例:

procedure TForm1.Button1Click(Sender: TObject);
begin
  TThread.CreateAnonymousThread(
    procedure
    var
      httpclient: TNetHTTPClient;
      output: string;
    begin
      httpclient := TNetHTTPClient.Create(nil);
      try
        httpclient.Asynchronous := False;
        output := httpclient.Get('https://google.com').ContentAsString;
      finally
        httpclient.Free;
      end;
    end).Start;
end;

当然,您也可以使用TTask或自定义线程来代替匿名线程。