2017-02-15 98 views
2

我使用Inno安裝程序安裝文檔/文件而不是應用程序,這主要針對Windows 7用戶。因此,我的DestDir基於{userdocs},因此所有文件都將安裝在該用戶文檔庫下的文件夾中。Inno安裝程序 - 從安裝程序訪問需要特權的非特權帳戶文件夾

當我使用相同的安裝程序安裝TTF字體時出現問題。這需要提升特權(adminsuperuser)。我看到的問題是,如果非管理員用戶運行安裝,則通過UAC正確提示管理員/超級用戶密碼...但在此時安裝的DestDir更改爲Admin文檔文件夾,而不是用戶的文檔文件夾。有什麼辦法可以解決這個問題或防止這種情況發生?

例,非管理員帳戶Fre具有的文件路徑:

C:\Users\Fred\My Documents\ 

如果我不包括TTF字體作爲安裝的一部分,這就是安裝程序會爲基礎路徑使用對於安裝{userdocs}和它完美的作品。

如果我不包括TTF字庫與同一非管理員用戶Fred在安裝過程中,由安裝完成{userdocs}已成爲

C:\Users\AdminUser\My Documents\ 

的時間......這不是想要的結果...只需要字體安裝部分的管理權限,並需要將文件安裝到實際用戶的文檔區域。

感謝。

+0

我已經添加了一個示例實現。 –

回答

1

爲字體創建子安裝程序,其中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; 

相關討論:

+0

第一個選項適合我的情況。非常感謝你。 –

相關問題