windows - Inno Setup - 从需要特权的安装程序访问非特权帐户文件夹

标签 windows installation inno-setup elevated-privileges

我使用 Inno Setup 来安装文档/文件而不是应用程序,这主要适用于 Windows 7 用户。因此,我的 DestDir 基于 {userdocs},因此所有文件都将安装在该用户文档库下方的文件夹中。

当我使用相同的安装程序安装 TTF 字体时,就会出现问题。这需要提升权限(adminsuperuser)。我看到的问题是,如果非管理员用户运行安装,则会通过 UAC 正确提示他们输入管理员/ super 用户密码...但此时安装的 DestDir 会发生变化到管理文档文件夹而不是用户的文档文件夹。有什么办法可以解决这个问题或防止这种情况发生吗?

例如,非管理员帐户 Fre 的文档路径为:

C:\Users\Fred\My Documents\

如果我不将 TTF 字体包含在安装过程中,安装程序将使用此字体作为安装 {userdocs} 的基本路径,并且它可以完美运行。

如果我确实将 TTF 字体包含在同一非管理员用户 Fred 的安装过程中,则安装完成时,{userdocs} 已变为

C:\Users\AdminUser\My Documents\ 

...这不是预期的结果...只需要字体安装部分的管理员权限,并且需要将文件安装到实际用户的文档区域中。

谢谢。

最佳答案

使用 PrivilegesRequired=admin directive 为字体创建子安装程序,您将从主非提升安装程序中运行。

主安装程序代码如下:

[Setup]
PrivilegesRequired=lowest

[Files]
Source: "ttfsetup.exe"; DestDir: {tmp}; Flags: deleteafterinstall

[Run]
Filename: "{tmp}\ttfsetup.exe"; Parameters: /silent; StatusMsg: "Installing TTF fonts..."

当然,您应该从主卸载程序中卸载子安装程序。

您可能还想确保用户没有明确以管理员权限运行主安装程序。请参阅我对 How to write to the user's My Documents directory with installer when the user used 'Run As Administrator' 的回答.

实现此目的的另一种方法是使用 ShellExec function使用 runas 动词来执行提升的外部复制实用程序( copyxcopyrobocopy )。请参阅Inno Setup - Register components as an administrator (它运行 regsvr32,但概念是相同的)。


另一个选项是从提升的安装程序执行非提升的进程,仅解析原始用户文档文件夹的路径。

使用ExecAsOriginalUser function .

您必须通过两个帐户都可以访问的一些临时文件来交换安装程序之间的路径。例如。 {commondocs} 中的文件,如Inno Setup always installs into admin's AppData directory中所示.

[Files]
Source: "*.txt"; DestDir: "{code:GetUserDocumentsFolder}"

[Code]

var
  UserDocumentsFolder: string;

function GetUserDocumentsFolder(Params: string): string;
begin
  Result := UserDocumentsFolder;
end;

function InitializeSetup(): Boolean;
var
  TempFile: string;
  Code: string;
  Buf: TArrayOfString;
  ResultCode: Integer;
begin
  Result := True;

  TempFile := { some path accessible by both users };
  Code :=
    '[Environment]::GetFolderPath(''MyDocuments'') | ' +
    'Out-File "' + TempFile + '" -Encoding UTF8';
  Log(Format('Executing: %s', [Code]));
  if (not ExecAsOriginalUser('powershell.exe', Code, '', SW_HIDE,
                             ewWaitUntilTerminated, ResultCode)) or
     (ResultCode <> 0) or
     (not LoadStringsFromFile(TempFile, Buf)) then
  begin
    MsgBox('Failed to resolve user MyDocuments path', mbError, MB_OK);
    Result := False;
  end
    else
  begin
    UserDocumentsFolder := Buf[0];
    Log(Format('User Documents path resolved to "%s"', [UserDocumentsFolder]));
  end;
end;

相关讨论:

关于windows - Inno Setup - 从需要特权的安装程序访问非特权帐户文件夹,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42256690/

相关文章:

c - 通过第三方插件在我的应用程序中实现绘图的更好方法是什么?

在 Windows 和 Linux 中使用 USB 访问的 Java 小程序

macos - 如何在 Mac 上启动 Grafana?

installation - 哪里可以下载最低限度的 JRE?

windows-phone-7 - .xap 文件未显示在 SD 卡中

windows - 如何自动更新使用 Inno Setup 安装的应用程序

inno-setup - 如果包含文件在包含后被删除,则 Inno Setup 在编译后显示 "Failed to open included file"错误消息

c# - 捕获 ASP.NET C# 中的所有异常,而不是捕获 `try{} catch{}` block 中的每个方法

visual-c++ - 确定处理器是 AMD64 还是 Intel64?

php 64 位 php_int_max = 2147483647