9

I am trying to use this code from the tutorial Getting version from MSI without installing it, but when I try to add the "msi.dll" to Visual Studio 2010 as a reference I get this error.

Could not load file or assembly 'msi.dll' or one of its dependencies. The module was expected to contain an assembly manifest.

This file may not be a managed assembly

5 Answers 5

20

Use "Microsoft.Deployment.WindowsInstaller.dll" from the Wix project's Deployment Tools Foundation (DTF). DTF provides a managed wrapper for much of msi.dll. Wix also provides helpful documentation.

Using DTF here is how I accessed the version number of an msi in C#

using Microsoft.Deployment.WindowsInstaller;

namespace Msi.Tables
{
    public class PropertyTable
    {
        public static string Get(string msi, string name)
        {
            using (Database db = new Database(msi))
            {
                return db.ExecuteScalar("SELECT `Value` FROM `Property` WHERE `Property` = '{0}'", name) as string;
            }
        }
        public static void Set(string msi, string name, string value)
        {
            using (Database db = new Database(msi, DatabaseOpenMode.Direct))
            {
                db.Execute("UPDATE `Property` SET `Value` = '{0}' WHERE `Property` = '{1}'", value, name);
            }
        }
    }
}

Then from my application

string msiVersion = PropertyTable.Get("MyInstall.msi", "ProductVersion");

You can use Orca to view the msi tables. MSDN provides documentation on the Property Table. The details on SQL syntax for Windows Installer is also available in MSDN

Sign up to request clarification or add additional context in comments.

4 Comments

The msi.dll assembly is installed by default in Windows XP and Windows 7 machine ? If not installed, what I need for installed it ?
This DLL is not included in Windows and is not part of Windows Installer. It's part of Windows Installer XML which can be found @ www.wixtoolset.org. You can deploy it privately with your application.
@ChristopherPainter Thanks for the correction! Deleted my erroneous comment :)
To find this package on NuGet search for 'DTF'
3

enter image description here

to register asembly on 32 bit machine

REGSVR32 MSI.DLL

to register asembly on 64 bit machine

cd \windows\syswow64 regsvr32 C:\WINDOWS\system32\msi.dll 

9 Comments

+1, the thing that tips you off to it being COM is the Activator.CreateInstance code in the tutorial.
Ya I also tried that as well. I have .net 4.0 console app and when I try to add that I get "Could not add a reference to {00C1902-00000-000-C000-0000000004...} Libary not registered (Exception from HRESULT:0x8002801D (Type_E_LIBNOTREGISTERED))
Tested same code in the tutorial with .net 4.0 console app and it is working without any issues.
Hmm made a new console and still does not work. Any idea on how to register it?
If you're on a 64bit machine, you may want to add /platform:x86 if it is only a 32bit COM library.
|
1

From codeproject:

To access the version number or other product related stuff, we need to have the DLL reference in Visual Studio .NET. DLL name: msi.dll (which exists in system32).

I think you should add reference to your project in Solution Explorer (right click on References in SE -> Add Reference -> then browse to msi.dll in system32 directory).

2 Comments

Sorry.Let me re-edit the question. The error I got is because of me trying to add msi.dll as a reference.
Not sure. I did not give you it.
0

Add system.management to references and include the namespace.

var searcher = new ManagementObjectSearcher("SELECT * FROM Win32_Product where Name LIKE '%Your MSI Name%'");

foreach (ManagementObject obj in searcher.Get())
{
  var version = obj["Version"];                
}

This will give you version of any software installed in control panel.

Comments

0
    var path = @"C:\Users\self\path\to\your\installFile.msi";
    var view = ((dynamic)Activator.CreateInstance(Type.GetTypeFromProgID("WindowsInstaller.Installer")))
        .OpenDatabase(path, 0)
        .OpenView("SELECT Value FROM Property WHERE Property = 'ProductVersion'");
    view.Execute();
    string version = view.Fetch().StringData(1);
    Console.WriteLine(version);

No references, no NuGets, no nothin'

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.