【问题标题】:Cannot delete connection definition 'It has associated connection'无法删除连接定义“它有关联的连接”
【发布时间】:2017-09-27 14:59:26
【问题描述】:

我的代码有一个设计时间TFDConnection。设置好参数,打开它,然后我从中派生一个 ConnectionDefinition 以供以后(同时)使用:

lParams.Assign(AConnection.Params);  (TStringList)
l := lParams.IndexOfName('Pooled');
if l <> -1 then
   lParams.Values['Pooled'] := 'true'
else
   lParams.Add('Pooled=true');
lConnName := AConnection.ConnectionName + 'Pooled';
if FDManager.IsConnectionDef(lConnName) then
   FDManager.DeleteConnectionDef(lConnName);
FDManager.AddConnectionDef(lConnName,AConnection.DriverName,lParams);

我有一个类型TTSQLScript

TTTSQLScripts = class(TComponent)
private
  FConn: TFDConnection;
  FScript: String;
public
  constructor Create(AOwner: TComponent; AConnection: TFDConnection); reintroduce;
  destructor Destroy; override;
  function Execute : Boolean;
  property Script : String read FScript write FScript;
end;

constructor TTTSQLScripts.Create(AOwner: TComponent; AConnection: TFDConnection);
begin
  inherited Create(AOwner);
  FConn := TFDConnection.Create(nil);
  // Pick up the pooled connection definition for concurrency:
  FConn.ConnectionDefName := AConnection.ConnectionName + 'Pooled';
  FConn.ResourceOptions.ParamExpand := false; 
  FScripts := TStringList.Create;
end;

destructor TTTSQLScripts.Destroy;
begin
  FConn.Close;
  FreeAndNil(FScripts);
  FreeAndNil(FConn);
  inherited;
end;

function TTTSQLScripts.Execute: Boolean;
begin
   try
      FConn.ExecSQL(FScript);
      Result := true;
   except
      Result := false;
   end;
end;

打开设计时连接后,我使用TTTSQLScripts组件:

lTTSQLScripts := TTTSQLScripts.Create(Application,ADataConnection);
lTTSQLScripts.Scripts.Text := 'some SQL';
lTTSQLScripts.Execute;
FreeAndNil(LTTSQLScripts);

问题

当我第二次设置我的设计时间TFDConnection 时,在上面的代码运行后,FDManager.DeleteConnectionDef 调用会触发:

[FireDac][Stan][Def]-251 无法定义 [xxxPooled]。它有关联的连接。

所以有些东西正在保持连接,但我看不到是什么。

上述结构中是否存在不正确或可疑的地方会导致这种情况?,
或者:当我尝试删除定义时,我能否找到有关仍然“关联”的连接的任何信息?

所有AConnection 传递的变量都引用我的设计时TFDConnection

添加:
我还尝试更改定义连接属性,但是一旦 TTTScripts 运行,这将失败并出现相同的错误:

var lDefCon: IFDStanConnectionDef;
lDefCon := FDManager.ConnectionDefs.ConnectionDefByName(cPooledName);
lDefCon.Params.Assign(lParams);
lDefCon.Apply;

【问题讨论】:

  • 我从来不需要删除连接定义。我要么在匹配时重用它,要么创建一个新的。据我了解,池连接实例在未使用且未销毁时会保留。因此,引用的连接 def 也必须可用。我也不明白,为什么要从现有连接创建连接 def。为什么不首先创建连接 def 并在所有地方使用它?
  • 至于最后一个问题:历史和陌生。我用 TFDConnection 替换了一个旧的设计时 TSDDatabase 组件。转换现有应用程序时,您不希望一次打开太多(例如用并行 TTask 替换所有这些线程)。但我会考虑你的建议。

标签: multithreading delphi database-connection firedac delphi-10.2-tokyo


【解决方案1】:

在设置新连接之前关闭 FDManager 似乎是最简单的解决方案。

很明显这会起作用,因为池连接也被删除了。

(这意味着我还没有深入了解问题,但我需要继续使用生产代码;我愿意花在修补上的限制。因此我不会将此答案标记为 解决方案)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-02-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多