2010-02-14 15 views
16

Ho letto tutti gli argomenti correlati e non ho trovato una risposta completa al mio problema.WIX: assegnazione delle autorizzazioni a una cartella

Desidero concedere autorizzazioni complete a SYSTEM e leggi & Esegui autorizzazioni per il gruppo Utenti in una cartella in Programmi. Niente di più, niente di meno.

So che ci sono 3 modi per dare autorizzazioni a una cartella utilizzando WIX, nessuno di loro sono veramente buono per me e ti spiego il perché:

1) regolare permesso elemento:

<CreateFolder Directory="Test"> 
     <Permission User="SYSTEM" GenericAll="yes"/> 
     <Permission User="Users" Domain="[LOCAL_MACHINE_NAME]" 
     GenericRead="yes" Read="yes" GenericExecute="yes" ChangePermission="yes"/> 
    </CreateFolder> 

Problema: Errore su sistema operativo estraneo poiché non conosce la parola chiave "Utenti". L'ho provato anche con SID. Accanto a questo ho bisogno di posizionare l'elemento Permission sotto ogni file nella directory di prova (ma se questo è stato l'unico caso, sarei riuscito)

2) WixUtilsExtension PermissionEx elemento:

<CreateFolder Directory="Test"> 
     <util:PermissionEx User="SYSTEM" GenericAll="yes"/> 
     <util:PermissionEx User="Users" Domain="[LOCAL_MACHINE_NAME]" 
     GenericRead="yes" Read="yes" GenericExecute="yes" ChangePermission="yes"/> 
    </CreateFolder> 

Problema: La cartella mantiene anche le autorizzazioni predefinite della cartella Programmi. Non posso permetterlo.

3) PermissionEx con Sddl:

Problema: Questo elemento è disponibile solo quando si installa con MSI 5.0. Sto usando il programma di installazione 3.01.

sarò felice di ricevere qualsiasi soluzione, comprese le soluzioni con azioni personalizzate ...

risposta

1

è necessario implementare un'azione personalizzata differita per la modifica delle autorizzazioni. c esempio # azione personalizzata:

[CustomAction] 
public static ActionResult SetFolderPermission(Session session) 
{ 
    string folder = session.CustomActionData["Folder"].Trim('\"'); 
    string sid = session.CustomActionData["SID"].Trim('\"'); 
    System.Security.Principal.SecurityIdentifier sidID = new System.Security.Principal.SecurityIdentifier(sid); 

    System.Security.AccessControl.DirectorySecurity ds = System.IO.Directory.GetAccessControl(folder); 
    ds.AddAccessRule(new System.Security.AccessControl.FileSystemAccessRule(sidID 
       , System.Security.AccessControl.FileSystemRights.Write 
       , System.Security.AccessControl.InheritanceFlags.ObjectInherit 
       , System.Security.AccessControl.PropagationFlags.NoPropagateInherit 
       , System.Security.AccessControl.AccessControlType.Allow)); 
    System.IO.Directory.SetAccessControl(folder , ds); 

    return ActionResult.Success; 
} 

si può porta che su C++, l'azione personalizzata deve essere differito - di quanto è necessario accedere ai tuoi proprietà della sessione da CustomActionData

2

Un'altra opzione sarebbe quella di avere un semplice CA che appena sarà traduce una proprietà msi che contiene il SID al nome effettivo del gruppo dal sistema operativo localizzato. La CA non deve essere posticipata e non sta facendo il vero lavoro di impostare le autorizzazioni.

Di seguito è riportato un esempio di CA che legge il valore della proprietà msi PROPERTY_TO_BE_TRANSLATED e traduce la proprietà msi indicata da esso. In questo modo è possibile eseguire la CA per tradurre diverse proprietà MSI.

[CustomAction] 
    public static ActionResult TranslateSidToName(Session session) 
    { 
    var property = session["PROPERTY_TO_BE_TRANSLATED"]; 
    if (String.IsNullOrEmpty(property)) 
    { 
     session.Log("The {0} property that should say what property to translate is empty", translateSidProperty); 
     return ActionResult.Failure; 
    } 
    var sid = session[property]; 
    if (String.IsNullOrEmpty(sid)) 
    { 
     session.Log("The {0} property that should contain the SID to translate is empty", property); 
     return ActionResult.Failure; 
    } 
    try 
    { 
     // convert the user sid to a domain\name 
     var account = new SecurityIdentifier(sid).Translate(typeof(NTAccount)).ToString(); 
     session[property] = account; 
     session.Log("The {0} property translated from {1} SID to {2}", property, sid, account); 
    } 
    catch (Exception e) 
    { 
     session.Log("Exception getting the name for the {0} sid. Message: {1}", sid, e.Message); 
     return ActionResult.Failure; 
    } 
    return ActionResult.Success; 
    } 

In WiX si definiscono le proprietà da tradurre utilizzando il SID for the accounts:

<Property Id="AdminAccount" Value="S-1-5-32-544" /> 
    <Property Id="EveryoneAccount" Value="S-1-1-0" /> 

Creare il CA che imposterà la proprietà PROPERTY_TO_BE_TRANSLATED e quindi chiamare il CA fare la traduzione:

<CustomAction Id="TranslateAdmin_SetProperty" Property="PROPERTY_TO_BE_TRANSLATED" Value="AdminAccount"/> 
<CustomAction Id="TranslateAdmin" BinaryKey="CommonCustomActions" DllEntry="TranslateSidToName" Impersonate="no" /> 
<CustomAction Id="TranslateEveryone_SetProperty" Property="PROPERTY_TO_BE_TRANSLATED" Value="EveryoneAccount" /> 
<CustomAction Id="TranslateEveryone" BinaryKey="CommonCustomActions" DllEntry="TranslateSidToName" Impersonate="no" /> 

Non dimenticare di utilizzare le proprietà msi quando si impostano le autorizzazioni:

<CreateFolder>     
    <Permission GenericAll="yes" User="[AdminAccount]" /> 
    <Permission GenericRead="yes" GenericExecute="yes" User="[EveryoneAccount]" /> 
</CreateFolder> 

Infine, pianificare il CA prima CreateFolder

<InstallExecuteSequence> 
    <Custom Action='TranslateAdmin_SetProperty' Before='TranslateAdmin' /> 
    <Custom Action='TranslateAdmin' Before='CreateFolders' /> 
    <Custom Action='TranslateEveryone_SetProperty' Before='TranslateEveryone' /> 
    <Custom Action='TranslateEveryone' Before='CreateFolders' /> 
    </InstallExecuteSequence> 

In questo modo il CA sta facendo solo qualche semplice lavoro, lasciando l'impostazione dei permessi per l'elemento WiX.

1

Come il <autorizzazione> elemento cancella l'eredità dei permessi da cartelle principali, si potrebbe provare a utilizzare un unico <permesso> elemento per gli utenti "tutti" o "Amministratori" seguito da < util: PermissionEx > elementi per impostare le autorizzazioni per i nomi utente non supportati dall'elemento <Permission>, ad esempio:

<Permission User="Everyone" GenericRead="no" /> 
<util:PermissionEx User="Users" Domain="[LOCAL_MACHINE_NAME]" GenericRead="yes" Read="yes" GenericExecute="yes" ChangePermission="yes" /> 

non è necessario impostare in modo esplicito il permesso per SYSTEM, in quanto questi vengono aggiunti automaticamente dal programma di installazione.

6

Utilizzare il codice seguente per eseguire questa operazione senza un'azione personalizzata. Ho verificato questo funziona (anche su cartelle figlio). Anche lo User Everyone è mappato su sistemi operativi Windows localizzati.

<CreateFolder> 
     <Permission User="Everyone" GenericAll="yes" ChangePermission="yes"/> 
</CreateFolder> 
+1

Questo non funzionerà per le lingue inglesi non statunitensi, perché "Tutti" deve essere localizzato. – John

+0

Non ho riscontrato problemi e lo distribuiamo a tutte le culture. Come l'hai aggiustato? –

6

Ho avuto lo stesso identico problema e ne ho parlato con Rob M. Stavo per rispondere a Christian G (https://stackoverflow.com/a/5296967/18475), ma Rob ha suggerito di utilizzare WixQueryOsWellKnownSID (http://wix.sourceforge.net/manual-wix3/osinfo.htm) per aggirare le locali non en-US.

Nel file .wxs si aggiunge la seguente:

<PropertyRef Id="WIX_ACCOUNT_LOCALSYSTEM" /> 
<PropertyRef Id="WIX_ACCOUNT_USERS" /> 

E più in basso nel file .wxs in cui si desidera applicare le autorizzazioni È proprio come questo:

<Permission GenericAll="yes" User="[WIX_ACCOUNT_LOCALSYSTEM]" /> 
<Permission GenericRead="yes" GenericExecute="yes" User="[WIX_ACCOUNT_USERS]" /> 

Ora, quando si esegue luce, devi solo collegare WixUtilExtension.

light -ext WiXUtilExtension ... 

NOTA: A seconda della versione di WiX, questo potrebbe non essere pienamente supportati. Se non funziona per te, potrebbero esserci altre opzioni che puoi utilizzare per translate SIDs.

+0

State attenti, penso che dovessimo sostenerlo per qualche motivo. – ferventcoder

+0

Questo non funziona per me.[WIX_ACCOUNT_USERS] verrà risolto in "BUILTIN \ Users" e concede l'autorizzazione a un utente chiamato "BUILTIN". –

+0

Il comportamento di cui sopra è vero solo se si impostano le autorizzazioni in un modulo unione! L'utilizzo di [WIX_ACCOUNT_USERS] in un progetto WiX e non in un modulo di unione WiX imposta correttamente le autorizzazioni per il gruppo di utenti. –