ISWIX, LLC View Christopher Painter's profile on LinkedIn profile for Christopher Painter at Stack Overflow, Q&A for professional and enthusiast programmers

January 17, 2007

Windows Installer Factory Provider for ADO.NET 2.0

I have to admit that for the last couple of months I really havn't spent much time working on installs. Instead I've been getting waist deep into C# programming, specifically ADO.NET 2.0 Factory Patterns. I guess that's what happens when you go to a new job to work with the founder of the Austin .NET User Group.

Although I've programmed on just about every platform and language over the years, Setup has always been deep in my blood. As I dug deeper and deeper into ADO.NET 2.0, I just couldn't help wonder what would be involved in making a Factory Provider for MSI databases. The goal would be to abstract .NET developer from the ugliness of the MSI API as much as possible. Every interop implementation that I've seen to date either was a direct wrap of the MSI API or Automation interface. Even the prettier ones like Rich's Pahvant.MSI still feels very MSI. What I wanted was the ability for anyone who's ever done ADO.NET to quickly be able to query and update MSI databases.

I've only barely begun on this project, but here is what I can report so far. It's really not that difficult to derive the classes needed from various abstract classes and interfaces. For example you can say:

using System;
using System.Data;
using System.Data.Common;
namespace System.Data.MSI
public sealed class
MSIFactory : DbProviderFactory
public static readonly MSIFactory
Instance = new MSIFactory();
public override DbCommand
return new MSICommand();
public override
DbCommandBuilder CreateCommandBuilder()
return new
public override DbConnection
return new MSIConnection();
public override
DbConnectionStringBuilder CreateConnectionStringBuilder()
return new
public override DbDataAdapter
return new MSIDataAdapter();
public override
DbParameter CreateParameter()
return new object() as

Then you create an App.Config file to teach the framework about your new Factory Class:

<?xml version="1.0" encoding="utf-8">
<remove invariant="System.Data.MSI"/>
<add name="MSI Data Provider" invariant="System.Data.MSI" description=".Net Framework Data Provider for MSI"
type="System.Data.MSI.MSIFactory, System.Data.MSI"/>

From there you go about defining each of your classes and wiring them up to communicate with the MSI API. Once this is all done it's time for the big payoff. Retrieving the contents of the Property table into a DataTable becomes as simple as:

using System;
using System.Data;
using System.Data.Common;
using System.Data.MSI;

DbProviderFactory factory =
DbConnection connection =
DbDataAdapter adapter =
DbCommand selectCommand =
DataTable propertyTable = new
connection.ConnectionString =

= connection;
selectCommand.CommandText = "SELECT * FROM
adapter.SelectCommand =

I have alot of work ahead of me, but I think this would be a really cool project to work on. I'm considering throwing this up on CodePlex if anyone would like to work on it with me. Just drop me a note. Until then, as Rob Mensching would say..... Keep on coding. You know I will.

No comments: