Может ли файл .msi установить сам (предположительно, через пользовательское действие)? - PullRequest
9 голосов
/ 18 сентября 2008

Я хочу создать MSI, который в процессе установки развернет себя вместе с содержащимися в нем файлами / компонентами в TargetDir.

Таким образом, MyApp.msi содержит MyApp.exe и MyAppBootstrapperEmpty.exe (без ресурсов) в своей таблице файлов.

Пользователь запускает MyAppBootstrapperPackaged.exe (содержащий MyApp.msi в качестве ресурса, полученного из Интернета, электронной почты или иным способом). MyAppBootStrapperPackaged.exe извлекает MyApp.msi во временную папку и выполняет его через msiexec.exe.

После завершения процесса msiexec.exe я хочу, чтобы MyApp.msi, MyBootstrapperEmpty.exe (И MyApp.exe в папке% ProgramFiles% \ MyApp, чтобы при запуске MyApp.exe был обеспечен доступ к MyApp.msi (для создания нижеуказанный упакованный контент).

MyAppBootstrapper * .exe может попытаться скопировать MyApp.msi в папку% ProgramFiles% \ MyApp, но для этого потребуется повышение прав и не позволит удалить его с помощью процесса удаления установщика Windows (из раздела «Установка и удаление программ» или другим способом). ), который следует сохранить.

Очевидно (я думаю, это очевидно - я ошибаюсь?) Я не могу включить MSI в качестве файла в мой Media / CAB (сценарий с курицей и яйцом), поэтому я считаю, что это должно быть сделано с помощью Custom Action перед процессом установки добавьте исходный MSI в Media / CAB DB MSI и соответствующую запись в таблице файлов на лету. Можно ли это сделать, и если да, то как?

Подумайте о модели распространения контента, в которой файлы контента распространяются только вместе с Приложением. Контент создается конечным пользователем через приложение во время выполнения и упаковывается в распространяемый EXE-файл, который включает в себя как приложение, так и контент.

Установщик MyApp должен оставаться MSI, но может выполняться Bootstrapper EXE. Установленный MyApp.exe должен иметь доступ как к MyApp.msi, так и к EXE, который должен быть "собран" во время выполнения приложением из базового (пустого) MyAppBootstrapper.exe, который также установлен MSI, и содержимого, созданного приложением. конечный пользователь. MSI-ресурс EXE-файла должен совпадать с тем, который использовался для установки приложения, выполняющего упаковку среды выполнения.

WIX не устанавливается с MyApp.

Не может быть никаких сетевых зависимостей во время выполнения / упаковки (т. Е. Не может выполнить упаковку через веб-сервис - должно выполняться локально).

Я знаком (и использую) пользовательские действия (управляемые и неуправляемые, через DTF и т. Д.).

Ответы [ 6 ]

9 голосов
/ 18 февраля 2009

Добавьте несжатый носитель к вашим wxs следующим образом:

<Media Id='2'/>

А затем создайте компонент с элементом File следующим образом:

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

Это заставит установщик искать файл с именем «myinstaller.msi» на установочном носителе, в той же папке, что и устанавливаемый файл msi. Приведенный выше исходный путь должен указывать на фиктивный файл, он только для того, чтобы успокоить wix.

Редактировать : следующий пример test.wxs демонстрирует, что он работает. Он создает файл test.msi, который устанавливается в папку c: \ program files \ test. Обратите внимание, что вам нужно поместить фиктивный файл test.msi в ту же папку, что и text.wxs, чтобы успокоить 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>
3 голосов
/ 18 сентября 2008

Наличие одного пакета .MSI для запуска другого пакета .MSI из "самого себя" называется вложенной установкой , и это плохо juju (см. Правило 20). Установщик Windows имеет некоторые глобальные данные, которые он использует для управления текущей установкой, и он не очень хорошо обрабатывает несколько установок одновременно. По той же причине, если вы запускаете одну установку, а затем пытаетесь запустить другую, пока первая еще не завершена, вы обычно увидите всплывающее окно с эффектом «выполняется другая установка, пожалуйста, подождите, пока она не будет завершена».

У вас может быть программа, обычно называемая загрузчиком (я думаю, это то, что вы имеете в виду), которая сама по себе не является установочным пакетом, но в которой содержит установочный пакет (например, MSI-файл). или .EXE) как ресурс, возможно сжатый. Действие программы начальной загрузки заключается в извлечении / развертывании ресурса в файл, обычно в каталоге %TEMP%, затем либо запуска извлеченного .EXE, либо запуска MSIEXEC на извлеченном .MSI. Загрузчик может содержать несколько ресурсов и извлекать + устанавливать их один за другим, если вам необходимо установить предварительные требования перед основным пакетом. Или вы можете отправить несколько пакетов в виде отдельных файлов, и загрузчик может выполнить / установить их непосредственно с дистрибутивного носителя один за другим, или скопировать их на целевой компьютер и запустить серию установки оттуда, или ...

Сам WiX не устанавливается, нет. Это инструмент, с помощью которого можно создавать пакеты .MSI. Проект WiX имеет в своем списке желаний общую программу начальной загрузки, но она еще не реализована. Доступны и другие бутстрэпперы, например этот .

Вам не потребуется настраиваемое действие - фактически, поскольку загрузчик сам по себе не является установочным пакетом установщика Windows, «настраиваемое действие» не имеет для него никакого значения. И, если вы достаточно знакомы с ЦС, чтобы знать об управляемом / неуправляемом / DTF, то вы знаете достаточно, чтобы избежать пользовательских действий, когда это возможно. (Оскал)

2 голосов
/ 20 сентября 2008

Я думаю, что вашему загрузчику гораздо проще извлечь MSI-файл в какое-то предопределенное место, чем во временную папку. Например, в C: \ Documents and Settings \ Все пользователи \ Данные приложения \ Моя компания \ Кэш установки моего продукта. После завершения установки загрузчик оставит MSI-файл там. Если на каком-то этапе пользователь решит переустановить ваш продукт, установщик Windows сможет найти исходный файл MSI.

Кроме того, добавьте путь к этому файлу в таблицу RemoveFile , чтобы он удалялся при удалении. Для этого вы можете использовать RemoveFile элемент в WiX.

1 голос
/ 18 сентября 2008

Так что, если я понимаю, тогда я думаю, что приложение должно создать преобразование (MST) с файлами содержимого и применить его к базовому MSI. Я все еще не убежден, что я понимаю все же. :)

0 голосов
/ 08 мая 2009

Я также работаю над способом развертывания нескольких файлов MSI. У меня есть программа bootstrapper.exe, которая связывает файлы MSI и запускает их по одному. Это решает мою проблему в большинстве случаев.

Случай, который он не решает, - это распределение объекта установки GPO (Global Policy Object). GPO требует файл dot-msi для запуска установки.

Для этого я сделал то, что почти решило проблему (но не совсем). Я помещаю файлы dot-msi в таблицу файлов установщика и помещаю свой загрузчик в двоичную таблицу и запускаю его из пользовательского действия, вставленного после InstallFinalize в InstallExecuteSequence. Конечно, загрузчик не сможет запускать другие MSI, потому что MSI верхнего уровня содержит мьютекс _MSIExecute.

Было довольно легко пройти немного дальше. Я заставил загрузчик вернуть управление установщику верхнего уровня и продолжить. Затем я добавил вызов WaitForSingleObject, чтобы дождаться окончания установки верхнего уровня, и загрузчик может продолжить установку.

Моя проблема заключается в том, что установка объекта групповой политики происходит во время загрузки, и установка верхнего уровня завершается до того, как будут выполнены вспомогательные установщики, и объект групповой политики перезагрузит компьютер.

Установка верхнего уровня также возвращает статус успешного завершения, когда установка может действительно произойти позже.

Я все еще ищу способ заблокировать установку верхнего уровня от завершения до завершения загрузчика.

0 голосов
/ 19 ноября 2008

Я бы настроил путь кеша MSI в известном месте.

Затем во время выполнения, если вам нужно "отредактировать" MSI, используйте VBScript или аналогичный.

Но все же я спрашиваю, ПОЧЕМУ!?!

...