mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-08-18 15:29:11 +02:00
fphttpclient: remove OnIdle and add protected methods so that the feature can be added in a descendant
This commit is contained in:
parent
67b08734cf
commit
008214ca15
@ -19,7 +19,7 @@ unit fphttpclient;
|
|||||||
interface
|
interface
|
||||||
|
|
||||||
uses
|
uses
|
||||||
Classes, SysUtils, ssockets, httpdefs, uriparser, base64, sslsockets, DateUtils;
|
Classes, SysUtils, ssockets, httpdefs, uriparser, base64, sslsockets;
|
||||||
|
|
||||||
Const
|
Const
|
||||||
// Socket Read buffer size
|
// Socket Read buffer size
|
||||||
@ -74,7 +74,6 @@ Type
|
|||||||
FKeepConnectionReconnectLimit: Integer;
|
FKeepConnectionReconnectLimit: Integer;
|
||||||
FMaxChunkSize: SizeUInt;
|
FMaxChunkSize: SizeUInt;
|
||||||
FMaxRedirects: Byte;
|
FMaxRedirects: Byte;
|
||||||
FOnIdle: TNotifyEvent;
|
|
||||||
FOnDataReceived: TDataEvent;
|
FOnDataReceived: TDataEvent;
|
||||||
FOnDataSent: TDataEvent;
|
FOnDataSent: TDataEvent;
|
||||||
FOnHeaders: TNotifyEvent;
|
FOnHeaders: TNotifyEvent;
|
||||||
@ -133,10 +132,6 @@ Type
|
|||||||
Function ProxyActive : Boolean;
|
Function ProxyActive : Boolean;
|
||||||
// Override this if you want to create a custom instance of proxy.
|
// Override this if you want to create a custom instance of proxy.
|
||||||
Function CreateProxyData : TProxyData;
|
Function CreateProxyData : TProxyData;
|
||||||
// Called before data is read.
|
|
||||||
Procedure DoBeforeDataRead; virtual;
|
|
||||||
// Called when the client is waiting for the server.
|
|
||||||
Procedure DoOnIdle;
|
|
||||||
// Called whenever data is read.
|
// Called whenever data is read.
|
||||||
Procedure DoDataRead; virtual;
|
Procedure DoDataRead; virtual;
|
||||||
// Called whenever data is written.
|
// Called whenever data is written.
|
||||||
@ -145,6 +140,10 @@ Type
|
|||||||
Function ParseStatusLine(AStatusLine : String) : Integer;
|
Function ParseStatusLine(AStatusLine : String) : Integer;
|
||||||
// Construct server URL for use in request line.
|
// Construct server URL for use in request line.
|
||||||
function GetServerURL(URI: TURI): String;
|
function GetServerURL(URI: TURI): String;
|
||||||
|
// Read raw data from socket
|
||||||
|
Function ReadFromSocket(var Buffer; Count: Longint): Longint; virtual;
|
||||||
|
// Write raw data to socket
|
||||||
|
Function WriteToSocket(const Buffer; Count: Longint): Longint; virtual;
|
||||||
// Read 1 line of response. Fills FBuffer
|
// Read 1 line of response. Fills FBuffer
|
||||||
function ReadString(out S: String): Boolean;
|
function ReadString(out S: String): Boolean;
|
||||||
// Write string
|
// Write string
|
||||||
@ -300,6 +299,8 @@ Type
|
|||||||
// Has Terminate been called ?
|
// Has Terminate been called ?
|
||||||
Property Terminated : Boolean Read FTerminated;
|
Property Terminated : Boolean Read FTerminated;
|
||||||
Protected
|
Protected
|
||||||
|
// Socket
|
||||||
|
Property Socket : TInetSocket read FSocket;
|
||||||
// Timeouts
|
// Timeouts
|
||||||
Property IOTimeout : Integer read FIOTimeout write SetIOTimeout;
|
Property IOTimeout : Integer read FIOTimeout write SetIOTimeout;
|
||||||
Property ConnectTimeout : Integer read FConnectTimeout write SetConnectTimeout;
|
Property ConnectTimeout : Integer read FConnectTimeout write SetConnectTimeout;
|
||||||
@ -353,8 +354,6 @@ Type
|
|||||||
Property OnPassword : TPasswordEvent Read FOnPassword Write FOnPassword;
|
Property OnPassword : TPasswordEvent Read FOnPassword Write FOnPassword;
|
||||||
// Called whenever data is read from the connection.
|
// Called whenever data is read from the connection.
|
||||||
Property OnDataReceived : TDataEvent Read FOnDataReceived Write FOnDataReceived;
|
Property OnDataReceived : TDataEvent Read FOnDataReceived Write FOnDataReceived;
|
||||||
// Called when the client is waiting for the server
|
|
||||||
Property OnIdle : TNotifyEvent Read FOnIdle Write FOnIdle;
|
|
||||||
// Called whenever data is written to the connection.
|
// Called whenever data is written to the connection.
|
||||||
Property OnDataSent : TDataEvent Read FOnDataSent Write FOnDataSent;
|
Property OnDataSent : TDataEvent Read FOnDataSent Write FOnDataSent;
|
||||||
// Called when headers have been processed.
|
// Called when headers have been processed.
|
||||||
@ -390,7 +389,6 @@ Type
|
|||||||
Property OnPassword;
|
Property OnPassword;
|
||||||
Property OnDataReceived;
|
Property OnDataReceived;
|
||||||
Property OnDataSent;
|
Property OnDataSent;
|
||||||
Property OnIdle;
|
|
||||||
Property OnHeaders;
|
Property OnHeaders;
|
||||||
Property OnGetSocketHandler;
|
Property OnGetSocketHandler;
|
||||||
Property Proxy;
|
Property Proxy;
|
||||||
@ -700,24 +698,13 @@ begin
|
|||||||
FreeAndNil(FSocket);
|
FreeAndNil(FSocket);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TFPCustomHTTPClient.DoBeforeDataRead;
|
function TFPCustomHTTPClient.ReadFromSocket(var Buffer; Count: Longint): Longint;
|
||||||
var
|
|
||||||
BreakUTC: TDateTime;
|
|
||||||
begin
|
begin
|
||||||
// Use CanRead to keep the client responsive in case the server needs a lot of time to respond.
|
Result:=FSocket.Read(Buffer,Count)
|
||||||
// The request can be terminated in OnIdle - therefore it makes sense only if FOnIdle is set
|
end;
|
||||||
If not Assigned(FOnIdle) Then
|
function TFPCustomHTTPClient.WriteToSocket(const Buffer; Count: Longint): Longint;
|
||||||
Exit;
|
begin
|
||||||
if IOTimeout>0 then
|
Result:=FSocket.Write(Buffer,Count)
|
||||||
BreakUTC := IncMilliSecond(NowUTC, IOTimeout);
|
|
||||||
while not Terminated and not FSocket.CanRead(10) and (FSocket.LastError=0) do
|
|
||||||
begin
|
|
||||||
DoOnIdle;
|
|
||||||
if (IOTimeout>0) and (CompareDateTime(NowUTC, BreakUTC)>0) then // we exceeded the timeout -> read error
|
|
||||||
Raise EHTTPClientSocketRead.Create(SErrReadingSocket);
|
|
||||||
end;
|
|
||||||
if FSocket.LastError<>0 then
|
|
||||||
Raise EHTTPClientSocketRead.Create(SErrReadingSocket);
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TFPCustomHTTPClient.AllowHeader(var AHeader: String): Boolean;
|
function TFPCustomHTTPClient.AllowHeader(var AHeader: String): Boolean;
|
||||||
@ -811,11 +798,10 @@ function TFPCustomHTTPClient.ReadString(out S: String): Boolean;
|
|||||||
R : Integer;
|
R : Integer;
|
||||||
|
|
||||||
begin
|
begin
|
||||||
DoBeforeDataRead;
|
|
||||||
if Terminated then
|
if Terminated then
|
||||||
Exit(False);
|
Exit(False);
|
||||||
SetLength(FBuffer,ReadBufLen);
|
SetLength(FBuffer,ReadBufLen);
|
||||||
r:=FSocket.Read(FBuffer[1],ReadBufLen);
|
r:=ReadFromSocket(FBuffer[1],ReadBufLen);
|
||||||
If (r=0) or Terminated Then
|
If (r=0) or Terminated Then
|
||||||
Exit(False);
|
Exit(False);
|
||||||
If (r<0) then
|
If (r<0) then
|
||||||
@ -884,7 +870,7 @@ begin
|
|||||||
|
|
||||||
T:=0;
|
T:=0;
|
||||||
Repeat
|
Repeat
|
||||||
r:=FSocket.Write(S[t+1],Length(S)-t);
|
r:=WriteToSocket(S[t+1],Length(S)-t);
|
||||||
inc(t,r);
|
inc(t,r);
|
||||||
DoDataWrite;
|
DoDataWrite;
|
||||||
Until Terminated or (t=Length(S)) or (r<=0);
|
Until Terminated or (t=Length(S)) or (r<=0);
|
||||||
@ -919,7 +905,7 @@ begin
|
|||||||
begin
|
begin
|
||||||
T:=0;
|
T:=0;
|
||||||
Repeat
|
Repeat
|
||||||
w:=FSocket.Write(PByte(Buffer)[t],i-t);
|
w:=WriteToSocket(PByte(Buffer)[t],i-t);
|
||||||
FRequestDataWritten:=FRequestDataWritten+w;
|
FRequestDataWritten:=FRequestDataWritten+w;
|
||||||
DoDataWrite;
|
DoDataWrite;
|
||||||
inc(t,w);
|
inc(t,w);
|
||||||
@ -1153,10 +1139,9 @@ Function TFPCustomHTTPClient.ReadResponse(Stream: TStream;
|
|||||||
Function Transfer(LB : Integer) : Integer;
|
Function Transfer(LB : Integer) : Integer;
|
||||||
|
|
||||||
begin
|
begin
|
||||||
DoBeforeDataRead;
|
|
||||||
if Terminated then
|
if Terminated then
|
||||||
Exit(0);
|
Exit(0);
|
||||||
Result:=FSocket.Read(FBuffer[1],LB);
|
Result:=ReadFromSocket(FBuffer[1],LB);
|
||||||
If Result<0 then
|
If Result<0 then
|
||||||
Raise EHTTPClientSocketRead.Create(SErrReadingSocket);
|
Raise EHTTPClientSocketRead.Create(SErrReadingSocket);
|
||||||
if (Result>0) then
|
if (Result>0) then
|
||||||
@ -1187,11 +1172,10 @@ Function TFPCustomHTTPClient.ReadResponse(Stream: TStream;
|
|||||||
|
|
||||||
begin
|
begin
|
||||||
Result:=False;
|
Result:=False;
|
||||||
DoBeforeDataRead;
|
|
||||||
If Terminated then
|
If Terminated then
|
||||||
exit;
|
exit;
|
||||||
SetLength(FBuffer,ReadBuflen);
|
SetLength(FBuffer,ReadBuflen);
|
||||||
Cnt:=FSocket.Read(FBuffer[1],length(FBuffer));
|
Cnt:=ReadFromSocket(FBuffer[1],length(FBuffer));
|
||||||
If Cnt<0 then
|
If Cnt<0 then
|
||||||
Raise EHTTPClientSocketRead.Create(SErrReadingSocket);
|
Raise EHTTPClientSocketRead.Create(SErrReadingSocket);
|
||||||
SetLength(FBuffer,Cnt);
|
SetLength(FBuffer,Cnt);
|
||||||
@ -1392,12 +1376,6 @@ begin
|
|||||||
End;
|
End;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TFPCustomHTTPClient.DoOnIdle;
|
|
||||||
begin
|
|
||||||
If Assigned(FOnIdle) Then
|
|
||||||
FOnIdle(Self);
|
|
||||||
end;
|
|
||||||
|
|
||||||
Procedure TFPCustomHTTPClient.DoKeepConnectionRequest(const AURI: TURI;
|
Procedure TFPCustomHTTPClient.DoKeepConnectionRequest(const AURI: TURI;
|
||||||
const AMethod: string; AStream: TStream;
|
const AMethod: string; AStream: TStream;
|
||||||
const AAllowedResponseCodes: array of Integer;
|
const AAllowedResponseCodes: array of Integer;
|
||||||
|
@ -180,7 +180,6 @@ type
|
|||||||
|
|
||||||
procedure OnDataReceived(Sender: TObject; const aContentLength, aCurrentPos: Int64);
|
procedure OnDataReceived(Sender: TObject; const aContentLength, aCurrentPos: Int64);
|
||||||
procedure OnDataSent(Sender: TObject; const aContentLength, aCurrentPos: Int64);
|
procedure OnDataSent(Sender: TObject; const aContentLength, aCurrentPos: Int64);
|
||||||
procedure OnIdle(Sender: TObject);
|
|
||||||
|
|
||||||
// the ExecOn* methods call their DoOn* counterparts - do the synchronisation here
|
// the ExecOn* methods call their DoOn* counterparts - do the synchronisation here
|
||||||
procedure ExecOnInit;
|
procedure ExecOnInit;
|
||||||
@ -253,6 +252,7 @@ type
|
|||||||
protected
|
protected
|
||||||
procedure Notification(AComponent: TComponent; Operation: TOperation); override;
|
procedure Notification(AComponent: TComponent; Operation: TOperation); override;
|
||||||
|
|
||||||
|
function CreatePool: TFPCustomHTTPClientPool; virtual;
|
||||||
function CreateRequestThread(aRequest: TFPHTTPClientAsyncPoolRequest; aClient: TFPHTTPClient): TFPHTTPClientAsyncPoolRequestThread; virtual;
|
function CreateRequestThread(aRequest: TFPHTTPClientAsyncPoolRequest; aClient: TFPHTTPClient): TFPHTTPClientAsyncPoolRequestThread; virtual;
|
||||||
function CreateWaitForAllRequestsThread(const aOnAllDone: TNotifyEvent; const aSynchronizeOnAllDone: Boolean;
|
function CreateWaitForAllRequestsThread(const aOnAllDone: TNotifyEvent; const aSynchronizeOnAllDone: Boolean;
|
||||||
const aOwner: TComponent; const aTimeoutMS: Integer): TFPHTTPClientAsyncPoolWaitForAllThread; virtual;
|
const aOwner: TComponent; const aTimeoutMS: Integer): TFPHTTPClientAsyncPoolWaitForAllThread; virtual;
|
||||||
@ -366,6 +366,7 @@ begin
|
|||||||
inherited OwnerDestroyed;
|
inherited OwnerDestroyed;
|
||||||
|
|
||||||
fOwner := nil;
|
fOwner := nil;
|
||||||
|
fOnAllDone := nil;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TFPHTTPClientAsyncPoolThread }
|
{ TFPHTTPClientAsyncPoolThread }
|
||||||
@ -601,6 +602,11 @@ begin
|
|||||||
InterlockedIncrement(fBlockRequestsCounter);
|
InterlockedIncrement(fBlockRequestsCounter);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
function TFPCustomHTTPClientAsyncPool.CreatePool: TFPCustomHTTPClientPool;
|
||||||
|
begin
|
||||||
|
Result := TFPCustomHTTPClientPool.Create(Self);
|
||||||
|
end;
|
||||||
|
|
||||||
function TFPCustomHTTPClientAsyncPool.CreateRequestThread(aRequest: TFPHTTPClientAsyncPoolRequest;
|
function TFPCustomHTTPClientAsyncPool.CreateRequestThread(aRequest: TFPHTTPClientAsyncPoolRequest;
|
||||||
aClient: TFPHTTPClient): TFPHTTPClientAsyncPoolRequestThread;
|
aClient: TFPHTTPClient): TFPHTTPClientAsyncPoolRequestThread;
|
||||||
begin
|
begin
|
||||||
@ -618,7 +624,7 @@ constructor TFPCustomHTTPClientAsyncPool.Create(AOwner: TComponent);
|
|||||||
begin
|
begin
|
||||||
fWorkingThreads := TThreadList.Create;
|
fWorkingThreads := TThreadList.Create;
|
||||||
fWaitingQueue := TList.Create;
|
fWaitingQueue := TList.Create;
|
||||||
fHttpPool := TFPCustomHTTPClientPool.Create(Self);
|
fHttpPool := CreatePool;
|
||||||
fDoOnAbortedFinishSynchronizedCS := TCriticalSection.Create;
|
fDoOnAbortedFinishSynchronizedCS := TCriticalSection.Create;
|
||||||
|
|
||||||
inherited Create(AOwner);
|
inherited Create(AOwner);
|
||||||
@ -986,12 +992,6 @@ begin
|
|||||||
OnDataReceivedSend(Sender, pdDataSent, aContentLength, aCurrentPos);
|
OnDataReceivedSend(Sender, pdDataSent, aContentLength, aCurrentPos);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TFPHTTPClientAsyncPoolRequestThread.OnIdle(Sender: TObject);
|
|
||||||
begin
|
|
||||||
if Terminated then
|
|
||||||
(Sender as TFPCustomHTTPClient).Terminate;
|
|
||||||
end;
|
|
||||||
|
|
||||||
procedure TFPHTTPClientAsyncPoolRequestThread.OwnerDestroyed;
|
procedure TFPHTTPClientAsyncPoolRequestThread.OwnerDestroyed;
|
||||||
begin
|
begin
|
||||||
inherited;
|
inherited;
|
||||||
@ -1026,47 +1026,19 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TFPHTTPClientAsyncPoolRequestThread.ExecOnFinish;
|
procedure TFPHTTPClientAsyncPoolRequestThread.ExecOnFinish;
|
||||||
var
|
|
||||||
xUnlocked: Boolean;
|
|
||||||
begin
|
begin
|
||||||
xUnlocked := False;
|
if Request.SynchronizeOnFinish then
|
||||||
LockProperties;
|
Synchronize(@DoOnFinish)
|
||||||
try
|
else
|
||||||
if Request.SynchronizeOnFinish then
|
DoOnFinish;
|
||||||
begin
|
|
||||||
UnlockProperties;
|
|
||||||
xUnlocked := True;
|
|
||||||
Synchronize(@DoOnFinish)
|
|
||||||
end
|
|
||||||
else
|
|
||||||
DoOnFinish;
|
|
||||||
finally
|
|
||||||
if not xUnlocked then
|
|
||||||
UnlockProperties;
|
|
||||||
end;
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TFPHTTPClientAsyncPoolRequestThread.ExecOnInit;
|
procedure TFPHTTPClientAsyncPoolRequestThread.ExecOnInit;
|
||||||
var
|
|
||||||
xUnlocked: Boolean;
|
|
||||||
begin
|
begin
|
||||||
xUnlocked := False;
|
if Request.SynchronizeOnInit then
|
||||||
LockProperties;
|
Synchronize(@DoOnInit)
|
||||||
try
|
else
|
||||||
if not Assigned(Request.OnInit) then
|
DoOnInit;
|
||||||
Exit;
|
|
||||||
|
|
||||||
if Request.SynchronizeOnInit then
|
|
||||||
begin
|
|
||||||
UnlockProperties;
|
|
||||||
xUnlocked := True;
|
|
||||||
Synchronize(@DoOnInit);
|
|
||||||
end else
|
|
||||||
DoOnInit;
|
|
||||||
finally
|
|
||||||
if not xUnlocked then
|
|
||||||
UnlockProperties;
|
|
||||||
end;
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TFPHTTPClientAsyncPoolRequestThread.ExecOnProgress(const aDirection: TFPHTTPClientPoolProgressDirection;
|
procedure TFPHTTPClientAsyncPoolRequestThread.ExecOnProgress(const aDirection: TFPHTTPClientPoolProgressDirection;
|
||||||
@ -1079,61 +1051,63 @@ procedure TFPHTTPClientAsyncPoolRequestThread.Execute;
|
|||||||
begin
|
begin
|
||||||
// don't LockProperties here - Request.Headers/ContentType/URLData/Method/URL/ResponseStream/AllowedResponseCodes are read-only
|
// don't LockProperties here - Request.Headers/ContentType/URLData/Method/URL/ResponseStream/AllowedResponseCodes are read-only
|
||||||
try
|
try
|
||||||
fClient.ConnectTimeout := Request.ConnectTimeout;
|
|
||||||
fClient.IOTimeout := Request.IOTimeout;
|
|
||||||
|
|
||||||
fClient.RequestHeaders.Text := Request.Headers;
|
|
||||||
if Request.ContentType<>'' then
|
|
||||||
fClient.AddHeader(fClient.RequestHeaders, HeaderContentType, Request.ContentType);
|
|
||||||
if Length(Request.URLData)>0 then
|
|
||||||
fClient.RequestBody := TBytesStream.Create(Request.URLData);
|
|
||||||
|
|
||||||
ExecOnInit;
|
|
||||||
|
|
||||||
fClient.OnDataReceived := @OnDataReceived;
|
|
||||||
fClient.OnDataSent := @OnDataSent;
|
|
||||||
fClient.OnIdle := @OnIdle;
|
|
||||||
|
|
||||||
if Terminated then
|
|
||||||
begin
|
|
||||||
fResult.MethodResult := mrAbortedByClient;
|
|
||||||
Exit;
|
|
||||||
end;
|
|
||||||
|
|
||||||
try
|
try
|
||||||
fClient.HTTPMethod(Request.Method, Request.URL, fResult.ResponseStream, Request.AllowedResponseCodes);
|
fClient.ConnectTimeout := Request.ConnectTimeout;
|
||||||
finally
|
fClient.IOTimeout := Request.IOTimeout;
|
||||||
fClient.RequestBody.Free;
|
|
||||||
fClient.RequestBody := nil;
|
fClient.RequestHeaders.Text := Request.Headers;
|
||||||
|
if Request.ContentType<>'' then
|
||||||
|
fClient.AddHeader(fClient.RequestHeaders, HeaderContentType, Request.ContentType);
|
||||||
|
if Length(Request.URLData)>0 then
|
||||||
|
fClient.RequestBody := TBytesStream.Create(Request.URLData);
|
||||||
|
|
||||||
|
ExecOnInit;
|
||||||
|
|
||||||
|
fClient.OnDataReceived := @OnDataReceived;
|
||||||
|
fClient.OnDataSent := @OnDataSent;
|
||||||
|
|
||||||
|
if Terminated then
|
||||||
|
begin
|
||||||
|
fResult.MethodResult := mrAbortedByClient;
|
||||||
|
Exit;
|
||||||
|
end;
|
||||||
|
|
||||||
|
try
|
||||||
|
fClient.HTTPMethod(Request.Method, Request.URL, fResult.ResponseStream, Request.AllowedResponseCodes);
|
||||||
|
finally
|
||||||
|
fClient.RequestBody.Free;
|
||||||
|
fClient.RequestBody := nil;
|
||||||
|
end;
|
||||||
|
fResult.ResponseStream.Position := 0;
|
||||||
|
if Terminated then
|
||||||
|
begin
|
||||||
|
fResult.MethodResult := mrAbortedByClient;
|
||||||
|
end else
|
||||||
|
begin
|
||||||
|
fResult.MethodResult := mrSuccess;
|
||||||
|
fResult.ResponseStatusCode := fClient.ResponseStatusCode;
|
||||||
|
fResult.ResponseStatusText := fClient.ResponseStatusText;
|
||||||
|
fResult.ResponseHeaders.Assign(fClient.ResponseHeaders);
|
||||||
|
end;
|
||||||
|
except
|
||||||
|
on E: TObject do
|
||||||
|
begin
|
||||||
|
if Terminated then // client terminated the connection -> it has priority above mrAbortedWithException
|
||||||
|
fResult.MethodResult := mrAbortedByClient
|
||||||
|
else
|
||||||
|
fResult.MethodResult := mrAbortedWithException;
|
||||||
|
fResult.ExceptionClass := E.ClassType;
|
||||||
|
if E is Exception then
|
||||||
|
fResult.ExceptionMessage := Exception(E).Message;
|
||||||
|
end;
|
||||||
end;
|
end;
|
||||||
fResult.ResponseStream.Position := 0;
|
finally
|
||||||
if Terminated then
|
try
|
||||||
begin
|
Pool.ReleaseClient(Request.URL, fClient);
|
||||||
fResult.MethodResult := mrAbortedByClient;
|
fClient := nil; // do not use fClient - it doesn't belong here anymore
|
||||||
end else
|
ExecOnFinish;
|
||||||
begin
|
except
|
||||||
fResult.MethodResult := mrSuccess;
|
|
||||||
fResult.ResponseStatusCode := fClient.ResponseStatusCode;
|
|
||||||
fResult.ResponseStatusText := fClient.ResponseStatusText;
|
|
||||||
fResult.ResponseHeaders.Assign(fClient.ResponseHeaders);
|
|
||||||
end;
|
end;
|
||||||
except
|
|
||||||
on E: TObject do
|
|
||||||
begin
|
|
||||||
if Terminated then // client terminated the connection -> it has priority above mrAbortedWithException
|
|
||||||
fResult.MethodResult := mrAbortedByClient
|
|
||||||
else
|
|
||||||
fResult.MethodResult := mrAbortedWithException;
|
|
||||||
fResult.ExceptionClass := E.ClassType;
|
|
||||||
if E is Exception then
|
|
||||||
fResult.ExceptionMessage := Exception(E).Message;
|
|
||||||
end;
|
|
||||||
end;
|
|
||||||
try
|
|
||||||
Pool.ReleaseClient(Request.URL, fClient);
|
|
||||||
fClient := nil; // do not use fClient - it doesn't belong here anymore
|
|
||||||
ExecOnFinish;
|
|
||||||
except
|
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user