* Close dataset on SQL change. Fixes issue #39610

(manually merged)
(cherry picked from commit a61d606643)
This commit is contained in:
Michaël Van Canneyt 2023-10-16 14:18:37 +02:00 committed by marcoonthegit
parent 3efadadfc5
commit 075e978367
2 changed files with 50 additions and 1 deletions

View File

@ -365,6 +365,7 @@ type
Private
FCursor : TSQLCursor;
FDatabase: TSQLConnection;
FOnSQLChanged: TNotifyEvent;
FParamCheck: Boolean;
FParams: TParams;
FMacroCheck: Boolean;
@ -423,6 +424,8 @@ type
Property ParseSQL : Boolean Read FParseSQL Write FParseSQL;
Property ParamCheck : Boolean Read FParamCheck Write FParamCheck default true;
Property MacroCheck : Boolean Read FMacroCheck Write SetMacroCheck default false;
Property InfoQuery : Boolean Read FInfoQuery Write FInfoQuery;
Property OnSQLChanged : TNotifyEvent Read FOnSQLChanged Write FOnSQLChanged;
Public
constructor Create(AOwner : TComponent); override;
destructor Destroy; override;
@ -474,7 +477,7 @@ type
{ TCustomSQLQuery }
TSQLQueryOption = (sqoKeepOpenOnCommit, sqoAutoApplyUpdates, sqoAutoCommit, sqoCancelUpdatesOnRefresh, sqoRefreshUsingSelect);
TSQLQueryOption = (sqoKeepOpenOnCommit, sqoAutoApplyUpdates, sqoAutoCommit, sqoCancelUpdatesOnRefresh, sqoRefreshUsingSelect, sqoNoCloseOnSQLChange);
TSQLQueryOptions = Set of TSQLQueryOption;
TCustomSQLQuery = class (TCustomBufDataset)
@ -524,6 +527,7 @@ type
function HasMacros: Boolean;
Function HasParams : Boolean;
Function NeedLastInsertID: TField;
procedure OnChangeSelectSQL(Sender: TObject);
procedure SetMacroChar(AValue: Char);
procedure SetOptions(AValue: TSQLQueryOptions);
procedure SetParamCheck(AValue: Boolean);
@ -933,6 +937,8 @@ var
NewParams: TSQLDBParams;
begin
if Assigned(FOnSQLChanged) then
FOnSQLChanged(Self);
UnPrepare;
RecreateMacros;
if not ParamCheck then
@ -2785,6 +2791,7 @@ begin
If ParamCheck and Assigned(FDataLink) then
(FDataLink as TMasterParamsDataLink).RefreshParamNames;
FQuery.ServerIndexDefs.Updated:=false;
end;
{ TCustomSQLQuery }
@ -2801,6 +2808,7 @@ constructor TCustomSQLQuery.Create(AOwner : TComponent);
begin
inherited Create(AOwner);
FStatement:=CreateSQLStatement(Self);
FStatement.OnSQLChanged:=@OnChangeSelectSQL;
FInsertSQL := TStringList.Create;
FInsertSQL.OnChange := @OnChangeModifySQL;
@ -3408,6 +3416,13 @@ begin
end
end;
procedure TCustomSQLQuery.OnChangeSelectSQL(Sender: TObject);
begin
if (sqoNoCloseOnSQLChange in Options) then
exit;
Close;
end;
procedure TCustomSQLQuery.SetMacroChar(AValue: Char);
begin
FStatement.MacroChar:=AValue;

View File

@ -61,6 +61,8 @@ type
procedure TestMacros;
Procedure TestPrepareCount;
Procedure TestNullTypeParam;
procedure TestChangeSQLCloseUnprepare;
procedure TestChangeSQLCloseUnprepareDisabled;
end;
{ TTestTSQLConnection }
@ -824,6 +826,38 @@ begin
SQLDBConnector.Connection.OnLog:=Nil;
end;
end;
procedure TTestTSQLQuery.TestChangeSQLCloseUnprepare;
begin
with SQLDBConnector.GetNDataset(10) as TSQLQuery do
begin
Open;
AssertTrue('Prepared after open', Prepared);
SQL.Text := 'SELECT * FROM FPDEV WHERE ID<0';
// statement must be unprepared when SQL is changed
AssertFalse('Prepared after SQL changed', Prepared);
// dataset remained active in FPC <= 3.2.2
AssertFalse('Active after SQL changed', Active);
SQL.Text := 'UPDATE FPDEV SET NAME=''Test'' WHERE ID>100';
ExecSQL;
end;
end;
procedure TTestTSQLQuery.TestChangeSQLCloseUnprepareDisabled;
begin
with SQLDBConnector.GetNDataset(10) as TSQLQuery do
begin
OPtions:=OPtions+[sqoNoCloseOnSQLChange];
Open;
AssertTrue('Prepared after open', Prepared);
SQL.Text := 'SELECT * FROM FPDEV WHERE ID<0';
// statement must be unprepared when SQL is changed
AssertFalse('Prepared after SQL changed', Prepared);
// dataset remained active in FPC <= 3.2.2
AssertTrue('Active after SQL changed', Active);
Close;
SQL.Text := 'UPDATE FPDEV SET NAME=''Test'' WHERE ID>100';
ExecSQL;
end;
end;
{ TTestTSQLConnection }