SetupProject

Muy buenas o no tan buenas si es que acabas de llegar de las vacaciones !😦

En esta ocasión y continuando con el tema de alguno de mis posts anteriores sobre los Setups (.msí) quiero comentar un pequeño truco para generar .msi en 64bits de forma automática.

Si habéis trabajado en la generación de “.msi” de 64bits y haciendo uso de las “Custom Actions”, habéis podido observar que una vez generado este, si se intenta instalar en una máquina de 64bits (a pesar de haber sido generado en 64bits), se obtiene el siguiente error:

Setup_Install_Error

¿Por que ocurre esto si realmente hemos generado un .msi de 64bits y lo estamos instalando en una maquina de 64?

Para dar solución a este tema tendremos que hacer uso de la herramienta “Orca” (o de alguna otra similar), ya postee sobre ella en mis inicios (“ORCA” – Windows Installer Table Editor) y mira por donde hoy, vuelvo a hacerle mención, ¡algo bueno tendrá!. Pues bien, esta herramienta nos va a permitir modificar uno de los valores de nuestro .msi con objeto de evitar este error debibo, parece ser a un “bug”, y que llevan ya tiempo sin querer solucionar. Para ello:

  • Siguiendo los pasos de mi anterior post “Compilando en 32 o en 64 bits”, bastará con que compilemos el proyecto “Setup1” para generar el fichero “Setup1.msi”.
  • Desde el “Orca” abrir “Setup1.msi” y buscar (Ctrl+F) “InstallUtil”.
  • Una vez localizado dicho valor, lo modificamos para que pase a tener este otro “C:\Windows\Microsoft.NET\Framework64\v2.0.50727\InstallUtilLib.dll”.  Como estaremos compilando en una máquina de 32bits no existirá esta ruta, no hay problema, la creamos manualmente y copiamos en ella la dll (InstallUtillLib.dll) que podemos conseguir de cualquier máquina que tenga instalado el framework de 64bits. Esto es necesario porque el Orca valida la existencia del fichero. “No lo he probado, pero me atrevería a segurar que podemos engañar al Orca creando un fichero de texto en blando y renombrandolo con este nombre sin necesidad de tener que tener dicha dll”).

Orca_InstallUtil

  • Ahora el .msi puede ser ejecutado sin errores en una máquina de 64bits.

 

Adicionalmente y con objeto de hacer esta labor de manera totalmente automática, seguiremos los siguientes pasos:

  • Generamos una pequeña aplicación de consola y añadimos una referencia COM “Microsoft Windows Installer Object Library”.
  • Añadimos a nuestra clase “program.cs” entre otro, el siguiente código:

            …Type classType = Type.GetTypeFromProgID(“WindowsInstaller.Installer“);
            Object installerClassObject = Activator.CreateInstance(classType);
            WindowsInstaller.Installer i = (WindowsInstaller.Installer)installerClassObject;

           
            WindowsInstaller.Database db = i.OpenDatabase(MSIFileSpec, WindowsInstaller.MsiOpenDatabaseMode.msiOpenDatabaseModeTransact);
            Console.WriteLine(“Running SQL Query for InstallUtil in the Binary MSI table“);

            // NOTE: The ` is correct in the SQL statement below – it is not ” or ‘
            WindowsInstaller.View v = db.OpenView(“SELECT `Name`,`Data` FROM `Binary` where `Binary`.`Name` = ‘InstallUtil’“);
            v.Execute(null);
            WindowsInstaller.Record Record = v.Fetch();
            if (Record != null)
            {
                Console.WriteLine(“Updating the Binary Data for InstallUtil“);
                Record.SetStream(2, InstallUtil64BitFileSpec);
                v.Modify(WindowsInstaller.MsiViewModify.msiViewModifyUpdate, Record);               
                ChangesMade = true;
            }
            else
            {
                Console.WriteLine(“Error : InstallUtil not found in the Binary MSI Table“);
            }
            v.Close();
            if (ChangesMade)
            {
                Console.WriteLine(“Commiting the changes to the database“);
                db.Commit();
            }….

Nota: Como se puede ver, lo que finalmente va a hacer nuestra aplicación de consola es exactamente lo mismo que hemos comentado anteriormente con nuestro amiga “Orca”.

  • Dotamos a la aplicación de consola del tratamiendo de un parámetro de entrada (ruta del “.msi” a editar).
  • Y, finalmente, solo nos queda tener ubicada esta aplicación en un sitio común para que todos nuestros proyecto de Setup la puedan utilizar:
    • Editamos la propiedad “PostBuildEvent” de cada uno de nuestros poryectos de setup y damos el valor “<AplicacionConsola> ruta_msi”.
    • El .msi generado ahora, ya puede instalarse directamente en una máquina de 64bits sin tener que hacer uso de Orca.

Nota: Si se genera un .msi de 64bits desde un entorno de desarrollo de 64bits esto no llega a ocurrir.

Os dejo aquí (“elGuerre.InstallUtilEditor.zip”) la aplicación de consola para que podáis utilizarla directamente.

Descarga “Orca” desde aquí.

Saludos
Juanlu