C# – How to read data from .msi file?

Today I start a new small project on extracting file from .msi file. The reason I start this project is that sometimes I just want to run a program only once but it needs to install on my machine. I do not like that. For example, I would like to check if my computer is suitable for Windows 7 so I downloaded Windows 7 Upgrade Advisor and run it to test. After finising with download, I realized that it is a .msi file. That means I must install if I would like to use. So I search around to find an unpacker for MSI file but after some searching I decide to write my own one. I guess it is not so difficult to write a program to extract all files in .msi file.

In my first step, I searched for MSI file format specification but after hard searching in 30 minutes, I could not find any documenation about msi file format. I really hate Microsoft in some cases. Microsoft did not publish any documentation of some important file formats and protocols which they use in Windows. Before I have problem with MMS protocol and now with MSI, always no specification for them. :(. I thought I could not start my project because it is not easy to reverse a file format of a complex structure. Luckily Wikipedia leads me to a WIX.

The Windows Installer XML toolset, is a free software toolset that builds Windows Installer (MSI) packages from an XML document. It supports a command-line environment that developers may integrate into their build processes to build MSI and MSM setup packages. WiX was the first software released by Microsoft under an open-source license called Common Public License.

For more details, you can find at homepage of Wix. I just post below a small code snippet to access info from msi file.

string strFileMsi = "D:\\w7ua.msi";
string strFileMsiNameOnly = Path.GetFileNameWithoutExtension(strFileMsi);
string strDirectory = Path.GetDirectoryName(strFileMsi);
Database dbMsiFile = new Database(strFileMsi, OpenDatabase.ReadOnly);
View viewTemp = dbMsiFile.OpenExecuteView("SELECT * FROM Media");
Record rcTemp = viewTemp.Fetch();
string strCabsName = rcTemp[CNST_MEDIA_CABINET];
strCabsName = strCabsName.Substring(1);
viewTemp = dbMsiFile.OpenExecuteView("SELECT * FROM `_Streams` WHERE `Name` = '" + strCabsName + "'");
rcTemp = viewTemp.Fetch();

To view all available tables from msi file you can use Orca tool which is shipped with Windows Installer 4.5 SDK as figure below.

1 comment

  1. Could you provide more details witch assembly are requred or at least the link to WiX page where the deyails coudl be found.

    I look on the WiX page and cant find such informations.

Leave a comment

Your email address will not be published. Required fields are marked *