【问题标题】:Setting up UDL connection at runtime in Delphi在 Delphi 中运行时设置 UDL 连接
【发布时间】:2019-10-01 10:08:16
【问题描述】:

在我们的 Delphi 应用程序中,我们使用 UDL 文件来存储连接属性。如果 UDL 文件丢失,那么我想创建它并让用户选择服务器/数据库并设置用户名/密码。然后它可以保存在 UDL 文件中,并在应用程序启动时一直使用。我知道这里存在安全问题,但这就是它在我的项目中的工作方式(我现在不打算更改它)。

UDL 文件应该在 'C:\Program Files (x86)\Common Files\system\ole db\Data Links' 文件夹中,通常它在那里。但是如果它丢失了,我想创建它并让用户在其中设置服务器/数据库等(每个客户都不同)。我已经知道如何创建 UDL 文件(使用 CreateUDLFile 函数)。但是如何在屏幕上弹出它以供用户完成设置。它应该是一种只进行一次的应用程序设置。现在可以手动完成(通过双击 UDL 文件),但我想自动化它。

这就是我想要弹出的内容:

【问题讨论】:

  • 看看文章here是不是如你所愿。
  • @MartynA,谢谢。我看到了那篇文章,但该代码只是创建了 UDL 文件。我已经知道该怎么做。我要做的是在屏幕上弹出创建的UDL文件(就像我双击它一样)。
  • 创建空的 .UDL 文件(如链接所述),然后使用 ShellExecute 启动 .UDL 文件。这将打开您的图像显示的对话框,允许用户对其进行编辑。
  • 或者作为替代方案,将 .UDL 文件作为资源文件包含在您的应用程序中。如果您的应用启动时 .UDL 文件不存在,您可以提取资源,将其保存到磁盘,然后ShellExecute 供用户编辑。
  • @Ken White,谢谢。我设法使它以这种方式工作。但是在我的情况下,我需要使用 ShellExecuteEx 并等待完成。我从另一个线程中使用了 ShellExecuteAndWait() 函数:link

标签: delphi delphi-xe


【解决方案1】:

这是我的问题的答案:

procedure TdmMain.DataModuleCreate(Sender: TObject);
var
  lDataLinkDir: String;
begin
  lDataLinkDir := DataLinkDir;
  if not FileExists(Format('%s\MBMIS.udl',[lDataLinkDir])) then
  begin
    if Copy(lDataLinkDir, Length(lDataLinkDir) - 1, 1) <> '\' then
      lDataLinkDir := lDataLinkDir + '\';
  // Creates empty UDL datalink.
  CreateUDLFile(lDataLinkDir + 'MBMIS.udl', 'SQLOLEDB.1', '');
  // Opens up the created UDL datalink for user to complete setup.
  ShellExecuteAndWait(lDataLinkDir + 'MBMIS.udl', '');
end;

{ Runs application using ShellExecuteEx and waits for completion. }
function TdmMain.ShellExecuteAndWait(FileName: String; Params: String): Boolean;
var
  exInfo: TShellExecuteInfo;
  Ph: DWORD;
begin
  FillChar(exInfo, SizeOf(exInfo), 0);
  with exInfo do
  begin
    cbSize := SizeOf(exInfo);
    fMask := SEE_MASK_NOCLOSEPROCESS or SEE_MASK_FLAG_DDEWAIT;
    Wnd := GetActiveWindow();
    exInfo.lpVerb := 'open';
    exInfo.lpParameters := PChar(Params);
    lpFile := PChar(FileName);
    nShow := SW_SHOWNORMAL;
  end;
  if ShellExecuteEx(@exInfo) then
    Ph := exInfo.hProcess
  else
  begin
    ShowMessage(SysErrorMessage(GetLastError));
    Result := true;
    exit;
  end;
  while WaitForSingleObject(exInfo.hProcess, 50) <> WAIT_OBJECT_0 do
    Application.ProcessMessages;
  CloseHandle(Ph);
  Result := true;
end;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多