Browse Source

* Force close during destroy, add event to report errors

Michaël Van Canneyt 1 year ago
parent
commit
151d72661a

+ 33 - 2
packages/fcl-db/src/base/database.inc

@@ -66,7 +66,7 @@ end;
 destructor TDatabase.Destroy;
 destructor TDatabase.Destroy;
 
 
 begin
 begin
-  Connected:=False;
+  CloseForDestroy;
   RemoveDatasets;
   RemoveDatasets;
   RemoveTransactions;
   RemoveTransactions;
   FDatasets.Free;
   FDatasets.Free;
@@ -650,6 +650,12 @@ begin
   FBeforeDisconnect:=AValue;
   FBeforeDisconnect:=AValue;
 end;
 end;
 
 
+procedure TCustomConnection.DoCloseError(aError: Exception);
+begin
+  if Assigned(FOnCloseError) then
+    FOnCloseError(Self,aError);
+end;
+
 procedure TCustomConnection.DoLoginPrompt;
 procedure TCustomConnection.DoLoginPrompt;
 
 
 var
 var
@@ -764,9 +770,34 @@ begin
   end;
   end;
 end;
 end;
 
 
+procedure TCustomConnection.CloseForDestroy;
+
+Const
+  MaxCount = 2;
+
+var
+  Force : Boolean;
+  aCount : Integer;
+begin
+  Force:=False;
+  aCount:=0;
+  While Connected and (aCount<MaxCount) do
+    try
+      Inc(aCount);
+      // Will set connected to false
+      Close(Force);
+    except
+      On E : Exception do
+        begin
+        Force:=True;
+        DoCloseError(E);
+        end;
+    end;
+end;
+
 destructor TCustomConnection.Destroy;
 destructor TCustomConnection.Destroy;
 begin
 begin
-  Connected:=False;
+  CloseForDestroy;
   Inherited Destroy;
   Inherited Destroy;
 end;
 end;
 
 

+ 5 - 0
packages/fcl-db/src/base/db.pas

@@ -2219,6 +2219,7 @@ type
   { TCustomConnection }
   { TCustomConnection }
 
 
   TLoginEvent = procedure(Sender: TObject; Username, Password: string) of object;
   TLoginEvent = procedure(Sender: TObject; Username, Password: string) of object;
+  TCloseErrorEvent = procedure(Sender : TObject; aError : Exception) of object;
 
 
   TCustomConnection = class(TComponent)
   TCustomConnection = class(TComponent)
   private
   private
@@ -2228,6 +2229,7 @@ type
     FBeforeDisconnect: TNotifyEvent;
     FBeforeDisconnect: TNotifyEvent;
     FForcedClose: Boolean;
     FForcedClose: Boolean;
     FLoginPrompt: Boolean;
     FLoginPrompt: Boolean;
+    FOnCloseError: TCloseErrorEvent;
     FOnLogin: TLoginEvent;
     FOnLogin: TLoginEvent;
     FStreamedConnected: Boolean;
     FStreamedConnected: Boolean;
     procedure SetAfterConnect(const AValue: TNotifyEvent);
     procedure SetAfterConnect(const AValue: TNotifyEvent);
@@ -2235,6 +2237,8 @@ type
     procedure SetBeforeConnect(const AValue: TNotifyEvent);
     procedure SetBeforeConnect(const AValue: TNotifyEvent);
     procedure SetBeforeDisconnect(const AValue: TNotifyEvent);
     procedure SetBeforeDisconnect(const AValue: TNotifyEvent);
   protected
   protected
+    Procedure DoCloseError(aError : Exception);
+    procedure CloseForDestroy;
     procedure DoLoginPrompt; virtual;
     procedure DoLoginPrompt; virtual;
     procedure DoConnect; virtual;
     procedure DoConnect; virtual;
     procedure DoDisconnect; virtual;
     procedure DoDisconnect; virtual;
@@ -2263,6 +2267,7 @@ type
     property BeforeConnect : TNotifyEvent read FBeforeConnect write SetBeforeConnect;
     property BeforeConnect : TNotifyEvent read FBeforeConnect write SetBeforeConnect;
     property BeforeDisconnect : TNotifyEvent read FBeforeDisconnect write SetBeforeDisconnect;
     property BeforeDisconnect : TNotifyEvent read FBeforeDisconnect write SetBeforeDisconnect;
     property OnLogin: TLoginEvent read FOnLogin write FOnLogin;
     property OnLogin: TLoginEvent read FOnLogin write FOnLogin;
+    Property OnCloseError : TCloseErrorEvent Read FOnCloseError Write FOnCloseError;
   end;
   end;
 
 
 
 

+ 1 - 1
packages/fcl-db/src/sqldb/sqldb.pp

@@ -1410,7 +1410,7 @@ end;
 destructor TSQLConnection.Destroy;
 destructor TSQLConnection.Destroy;
 begin
 begin
   try
   try
-    Connected:=False; // needed because we want to de-allocate statements
+    CloseForDestroy; // needed because we want to de-allocate statements
   Finally  
   Finally  
     FreeAndNil(FStatements);
     FreeAndNil(FStatements);
     inherited Destroy;
     inherited Destroy;