um arquivo .msi pode instalar-se (presumivelmente por meio de uma ação personalizada)?

StackOverflow https://stackoverflow.com/questions/88078

  •  01-07-2019
  •  | 
  •  

Pergunta

I varinha para construir um MSI que, no seu processo de instalação, vai implantar-se, juntamente com a sua continha ficheiros / Componentes, para o TargetDir.

Assim MyApp.msi contém MyApp.exe e MyAppBootstrapperEmpty.exe (sem recursos) em sua tabela de arquivos.

O usuário lança uma MyAppBootstrapperPackaged.exe (contendo MyApp.msi como um recurso, obtido a partir da algures internet, ou e-mail ou não). MyAppBootStrapperPackaged.exe extratos MyApp.msi para uma pasta temporária e executa-lo através msiexec.exe.

Depois da conclusão do processo de Msiexec.exe, quero MyApp.msi, MyBootstrapperEmpty.exe (AND MyApp.exe em% ProgramFiles% \ MyApp pasta para MyApp.exe pode ser assegurado o acesso ao MyApp.msi quando ele é executado (para a criação de o conteúdo embalado abaixo mencionados).

MyAppBootstrapper * .exe poderia tentar copiar MyApp.msi para MyApp pasta% ProgramFiles% \, mas precisaria de elevação para fazê-lo, e não permitiria a sua remoção por meio de processo de desinstalação do Windows Installer (a partir de Adicionar / Remover Programas ou de outra forma ), que deve ser preservado.

Obviamente (eu acho que é óbvio - estou errado?) Eu não posso incluir o MSI como um arquivo no meu Mídia / CAB (frango e ovo cenário), então eu acredito que teria que ser feito através de uma ação personalizada antes do processo de instalação, acrescentando que a MSI original da MSI DB mídia / CAB e a entrada apropriada na tabela de arquivos on the fly. isso pode ser feito e de que forma?

Pense em um modelo de distribuição de conteúdo onde os arquivos de conteúdo são sempre apenas para ser distribuído em conjunto com a App. O conteúdo é produzido pelo utilizador final através da aplicação em tempo de execução, e empacotado em um EXE distribuível que inclui tanto a App e o conteúdo.

O instalador do MyApp deve permanecer um MSI, mas pode ser executado por um Bootstrapper EXE. O MeuAplic.exe instalado deve ter acesso a ambos e MyApp.msi EXE é para ser "reunido" em tempo de execução pelo aplicativo de uma base (vazio) MyAppBootstrapper.exe, que também é instalado pela MSI, e o conteúdo criado pela usuário final. recurso do EXE MSI deve ser a mesma que a utilizada para instalar o App que está fazendo a embalagem tempo de execução.

WIX não é para ser instalado com MyApp.

Não pode haver dependências da rede em run- / embalagem- tempo (ou seja, não pode fazer a embalagem através de um Webservice - deve ser feito localmente)

.

Eu estou familiarizado com (e usar) Custom Actions (gerenciados e não gerenciados, via DTF e de outra forma).

Foi útil?

Solução

Adicionar um meio não comprimido a seus wxs assim:

<Media Id='2'/>

E, em seguida, criar um componente com um elemento de arquivo como este:

<File Source='/path/to/myinstaller.msi' Compressed='no' DiskId='2' />

Isso fará com que o olhar instalador para um arquivo chamado "myinstaller.msi" no meio de instalação, na mesma pasta que o msi que está sendo instalado. O caminho de origem acima deve apontar para um arquivo fictício, é apenas lá para Wix apaziguar.

Editar : Os seguintes test.wxs exemplo demonstra que ele funciona. Ele produz um arquivo test.msi que se instala em c: \ test arquivos de programas \. Note que você precisa colocar um arquivo fictício test.msi na mesma pasta como text.wxs para apaziguar wix.

<?xml version='1.0' encoding='utf-8'?>
<Wix xmlns='http://schemas.microsoft.com/wix/2006/wi'>
   <Product
         Name='ProductName'
         Id='*'
         Language='1033'
         Version='0.0.1'
         Manufacturer='ManufacturerName' >
      <Package
            Keywords='Installer'
            Description='Installer which installs itself'
            Manufacturer='ManufactererName'
            InstallerVersion='100'
            Languages='1033'
            Compressed='yes'
            SummaryCodepage='1252'/>

      <Media Id='1' Cabinet='test.cab' EmbedCab='yes'/> 
      <Media Id='2' /> 

      <Directory Id='TARGETDIR' Name="SourceDir">
         <Directory Id='ProgramFilesFolder'>
            <Directory Id='TestFolder' Name='Test' >
               <Component Id="InstallMyself">
                  <File Source="./test.msi" Compressed="no" DiskId="2" />
               </Component>
            </Directory>
         </Directory>
      </Directory>

      <Feature
            Id='Complete'
            Display='expand'
            Level='1'
            Title='Copy msi file to program files folder'
            Description='Test'>

         <ComponentRef Id="InstallMyself" />
      </Feature>

   </Product>
</Wix>

Outras dicas

Ter um lançamento pacote .msi outro pacote .msi a partir de "dentro" em si é chamado de aninhada instalar , e de mau juju (ver Regra 20). Windows Installer tem alguns dados global, que ele usa para gerenciar instalar o atual, e não segurar bem várias instalações, ao mesmo tempo. Pela mesma razão, se você iniciar um instalar e, em seguida, tentar iniciar o outro enquanto o primeiro ainda está em andamento, normalmente você vai ver um pop-up para o efeito de "outra instalação em andamento, aguarde até que seja feito".

Você pode ter um programa, geralmente chamado de bootstrapper (acho que é isso que você está se referindo), que em si não é um pacote de instalação, mas que contém um pacote de instalação (como um. MSI ou um .exe) como um recurso, possivelmente comprimido. A ação do programa bootstrapper é extrair / expandir o recurso para um arquivo, geralmente em um diretório %TEMP%, em seguida, quer lançar o .EXE extraído ou executar MSIEXEC na MSI extraído. O bootstrapper pode conter vários recursos e extrato + instalá-los um por um, se você precisa instalar os pré-requisitos antes de o pacote principal. Ou você pode enviar vários pacotes como arquivos separados, e têm o bootstrapper executar / instalá-los directamente a partir da uma mídia de distribuição por um, ou copiá-los para baixo para a máquina de destino e executar a série de instalar a partir de lá, ou ...

si WiX não é instalado, não. É uma ferramenta com a qual pacotes .msi pode ser construída. O projeto WiX tem em sua lista um programa bootstrapper genérico, mas ainda não foi implementado. Há outros bootstrappers disponíveis, v.g. esta .

Você não vai precisar de uma ação personalizada - na verdade, uma vez que o bootstrapper não é em si um pacote de instalação do Windows Installer "ação personalizada" não tem nenhum significado para ele. E, se você for suficientemente familiarizado com CAs de saber sobre gerenciado / / DTF, então você sabe o suficiente para ações personalizadas Evitar sempre que puder. (Sorriso)

Eu acho que é muito mais fácil para o seu bootstrapper para extrair arquivo MSI para algum local predefinido em vez de para a pasta Temp. Por exemplo, para C: \ Documents and Settings \ All Users \ Application Data \ Minha Empresa \ do Produto Instale Cache. Após a conclusão da instalação bootstrapper deixaria arquivo MSI sentado lá. Se em algum utilizador estágio decide a reinstalação do produto Windows Installer será capaz de localizar o arquivo MSI fonte.

Além disso, adicionar caminho para esse arquivo para RemoveFile mesa assim que fica excluído na desinstalação. Você pode usar RemoveFile elemento em WiX para isso.

Então, se eu entendi, então eu acho que eu teria o aplicativo criar uma transformação (MST) que tem os arquivos de conteúdo e aplicar isso para a base MSI. Eu ainda não estou convencido de que eu entendo embora. :)

Eu configurar o caminho de cache MSI em um local conhecido.

Em seguida, em tempo de execução se você precisar "editar" o MSI uso VBScript ou similar.

Mas ainda assim, eu pergunto porque!?!

Também estou trabalhando em uma maneira de implantar vários arquivos MSI.Eu tenho um programa bootstrapper.exe que agrupa os arquivos MSI e os executa um de cada vez.Isso resolve meu problema na maioria dos casos.

O caso que não resolve é a distribuição GPO (Global Policy Object) da instalação.O GPO requer um arquivo dot-msi para executar uma instalação.

Para fazer isso, aqui está o que fiz que quase resolveu o problema (mas não totalmente).Coloquei os arquivos dot-msi na tabela de arquivos de um instalador e coloquei meu bootstrapper na tabela binária e executei-o a partir de uma ação customizada inserida após InstallFinalize no InstallExecuteSequence.É claro que o bootstrapper não será capaz de executar outros MSIs porque o MSI de nível superior contém o mutex _MSIExecute.

Foi muito fácil chegar um pouco mais longe.Fiz o bootstrapper retornar o controle para o instalador de nível superior e continuar.E então adicionei uma chamada WaitForSingleObject para aguardar a conclusão da instalação de nível superior e o bootstrapper pode continuar a concluir a instalação.

Meu problema é que a instalação do GPO acontece no momento da inicialização e a instalação de nível superior é concluída antes que os subinstaladores sejam concluídos e o GPO reinicialize a máquina.

A instalação de nível superior também retorna um status de sucesso quando a instalação pode falhar posteriormente.

Ainda estou procurando uma maneira de impedir a conclusão da instalação de nível superior até a conclusão do bootstrapper.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top