WMI or Windows Management Instrumentation has been around for years. As a .NET developer and a DBA I have been using it to collect information about the servers in my enterprise. WMI gives me the ability to collect information about important things such as disk space, OS patch levels and ACLs. The cool thing about WMI is that it uses a SQL like syntax. This makes it easy for most developers to use because we typically all have experience using T-SQL.
In case you didn't know, most management tools like SCOM and HP Openview will leverage WMI to pull information from servers. In addition, certain applications like SQL Server will register a set of WMI classes during the install. Lets start out by looking at a sample WMI query that retrieves some basic OS information from a server:
SELECT
Caption,
TotalVirtualMemorySize,
ServicePackMajorVersion,
ServicePackMinorVersion
FROM
Win32_OperatingSystem
Pretty simple, huh? Now lets take this query and integrate it with our C# code
//Connect to the remote computer
ConnectionOptions co = new ConnectionOptions();
co.Authentication = AuthenticationLevel.Default;
//Point to machine
System.Management.ManagementScope ms =
new System.Management.ManagementScope("\\\\" + ServerName + "\\root\\cimv2", co);
string sql = @"SELECT
Caption,
TotalVirtualMemorySize,
ServicePackMajorVersion,
ServicePackMinorVersion
FROM
Win32_OperatingSystem";
System.Management.ObjectQuery oq = new System.Management.ObjectQuery(sql);
ManagementObjectSearcher query = new ManagementObjectSearcher(ms, oq);
query.Options.Timeout = new TimeSpan(0, 0, 60);
Console.WriteLine( "Operating System: " + mo["Caption"].ToString() );
Console.WriteLine( "Memory: " + mo["TotalVirtualMemorySize"].ToString() );
Console.WriteLine( "Service Pack: " + mo["ServicePackMajorVersion"].ToString() +
"." + mo["ServicePackMinorVersion"].ToString() );
The code is pretty straightforward. You connect to a server, run the WMI query and then read the results. In my environment I wrote a service which reads all the server names from a database and then makes a series of WMI calls to each server to collect the relevant information. Then I wrote a ASP.NET MVC application which displays alerts to the various support personnel. Lets take a look at a one more example, which uses a WMI query to collect disk information:
SELECT
FreeSpace,
Size,
Name,
VolumeName
from
WIN32_LogicalDisk
where
DriveType = 3
Notice that I filter on disks where the DriveType = 3. This eliminates CD drives, floppies, and network drives. As a DBA I am only concerned with certain volumes. Finally, this example query can return multiple records because most servers have more than one drive. So we now loop over the query results to read the values
foreach (ManagementObject mo in query.Get())
{
Console.WriteLine( "Name: " + mo["Name"].ToString() );
Console.WriteLine( "Size: " + mo["Size"].ToString() );
Console.WriteLine( "Free Space: " + mo["FreeSpace"].ToString() );
}
These two examples are just the tip of the iceberg. There are tons of WMI classes that you can query. Microsoft has a complete WMI reference posted on MSDN. If you just want to run a few WMI queries without writing C# code than you can download the WMI Adminstrative Tools from Microsoft and try it out.
Additional Resources:
Troubleshooting WMI - If you have problems getting your queries to run please view this page first. Windows Firewall or security permissions may need to be modified
WMI reference - The complete list of WMI classes.
WMI Adminstrative Tools - Tools you can use to query your servers with WMI.