2013-04-19 13 views
11

Desidero che l'installazione fallisca se non è installato un elemento software di terze parti. Ho aggiunto uno Fragment con uno util:RegistrySearch e uno bal:Condition allo Bundle, ma non riesco a farlo funzionare. ThirdPartyCOMLibraryInstalled mai valutato come true. Ho confermato che la chiave esiste e il valore che utilizzo per Key è corretto: copio/incollato il nome dalla chiave selezionata in regedit. Non ci sono errori nel registro.Bundle WiX bal: condizione - util: variabile RegistrySearch sempre falsa

sto costruendo il programma di installazione con WiXTools 3.7 in Visual Studio 2012 su Windows   7 64-bit e il test sia su Windows XP SP3   e Windows   7 64-bit.

Ricerca in linea per altri esempi per util:RegistrySearch Ho trovato i seguenti moduli alternativi per l'espressione del condition condition.

  1. ThirdPartyCOMLibraryInstalled = 0 - sempre False
  2. ThirdPartyCOMLibraryInstalled <> 1 - sempre vero

ecco il codice Bundle:

<?xml version="1.0" encoding="UTF-8"?> 
<Wix xmlns="http://schemas.microsoft.com/wix/2006/wi" 
    xmlns:util="http://schemas.microsoft.com/wix/UtilExtension" 
    xmlns:netfx="http://schemas.microsoft.com/wix/NetFxExtension" 
    xmlns:bal="http://schemas.microsoft.com/wix/BalExtension"> 

    <Bundle Name="!(bind.packageName.MyApp)" 
      Version="!(bind.packageVersion.MyApp)" 
      Manufacturer="!(bind.packageManufacturer.MyApp)" 
      UpgradeCode="a07ce1d5-a7ed-4d89-a7ee-fb13a5dd69ba" 
      Copyright="Copyright (c) 2013 [Bundle/@Manufacturer]. All rights reserved." 
      IconSourceFile="$(var.My_Application1.ProjectDir)MyCo.ico"> 

     <bal:Condition Message="ThirdParty Application COM Library Required. Please (re)install ThirdParty Application and ensure 'Windows API' and '.NET Components' are installed." 
     >ThirdPartyCOMLibraryInstalled</bal:Condition> 

     <Variable Name="InstallFolder" 
        Type="string" 
        Value="[ProgramFilesFolder]MyCo Systems\My_Application\"/> 
     <BootstrapperApplicationRef 
      Id="WixStandardBootstrapperApplication.HyperlinkLicense" > 

      <bal:WixStandardBootstrapperApplication 
       ThemeFile="Resources\HyperlinkTheme.xml" 
       LaunchTarget="[InstallFolder]My_Application.exe" 
       LocalizationFile="Resources\HyperlinkTheme.wxl" 
       SuppressRepair="yes" 
       SuppressOptionsUI="yes" 
       LicenseUrl="" 
       LogoFile="Resources/MyCoLogoWt64.png" 

      /> 
     </BootstrapperApplicationRef> 
     <Chain> 
      <PackageGroupRef Id="NetFx40Redist"/> 
      <MsiPackage Id ="MyApp" 
         Vital="yes" 
         Name="My Application" 
         SourceFile="$(var.MyApp_Install.TargetDir)MyApp_Install.msi"> 
       <MsiProperty Name="INSTALLLOCATION" 
          Value="[InstallFolder]" /> 
      </MsiPackage> 
     </Chain> 
    </Bundle> 

    <Fragment> 
     <util:RegistrySearch 
      Variable="ThirdPartyCOMLibraryInstalled" 
      Result="exists" 
      Root="HKLM" 
      Key="SOFTWARE\Classes\ThirdPartyId.Server\CLSID"/> 
    </Fragment> 
</Wix> 

risposta

13

Il problema principale è che il RegistrySearch è in un separato Fragment che mai viene referenziato. Poiché nulla nel Fragment viene referenziato, il linker "ottimizza" il contenuto dello Fragment e la ricerca non è inclusa nel tuo Bundle.

parte: si potrebbe sostenere che il fatto che v'è un riferimento alla variabile di cui la ricerca nella Condition che il linker dovrebbe essere in grado di capire che la ricerca è necessaria. Tuttavia, ciò non funziona in tutti i casi.

Fortunatamente, la soluzione è abbastanza semplice! Si nemmeno bisogno di scegliere uno dei due:

  1. spostare l'elemento RegistrySearch all'elemento Bundle.
  2. Aggiungere un elemento RegistrySearchRef nell'elemento Bundle per fare riferimento allo RegistrySearch nello Fragment. Dovrai inoltre fornire l'attributo RegistrySearch e Id.

Personalmente, mi piace l'opzione due e probabilmente anche spostare il Condition nella Fragment così di raggruppare tutta quella roba insieme. Qualcosa di simile a:

<Bundle ...> 
    <util:RegistrySearchRef Id='SearchForThirdParty' /> 

    ... 

</Bundle> 

<Fragment> 
    <util:RegistrySearch 
      Id='SearchForThirdParty' 
      Variable="ThirdPartyCOMLibraryInstalled" 
      Result="exists" 
      Root="HKLM" 
      Key="SOFTWARE\Classes\ThirdPartyId.Server\CLSID"/> 

    <bal:Condition Message="ThirdParty Application COM Library Required. Please (re)install ThirdParty Application and ensure 'Windows API' and '.Net Components' are installed.">ThirdPartyCOMLibraryInstalled</bal:Condition> 
    </Fragment> 
</Wix> 

Che dovrebbe farlo.

+1

Che funziona esattamente. Grazie. Sarei felice di averlo pubblicato sulla documentazione WiX come una delle "Guide", ad esempio "Bloccare l'installazione bootstrapper in base a una chiave di registro mancante" Che cosa posso fare per farlo? –

+0

Sembra buono. Per aggiungere aiuto, invia una richiesta di pull sul ramo wix38 con le modifiche ai file sotto: 'src \ chm \ html'. Il codice è disponibile all'indirizzo http://wix.codeplex.com/ –

+0

Vedere la richiesta di pull su codeplex. –