This is the third post on the series “create a macro to Attach to Local IISâ€. The last modification I want to implement is the ability to list all the w3wp.exe active processes, if more than one process is present, I want it to show a list of all IIS processes and let the user choose the list of processes to attach to. Clearly if I have no w3wp.exe active processes, or I have only one, there is no need to bother the user to choose the single available process.
Since I need to show a “user interface†from a macro and I’m not allowed to insert form into Visual Studio Macros Editor, I should create a Windows Forms programmatically. This is quite annoying, but creating simple interfaces without a designer is quite simple, so it is the right approach to maintain the code in a simple macro. First of all I find all IIS processes and add info about these processes inside a ListView.
1: Dim dbg2 As EnvDTE80.Debugger2 = DTE.Debugger
2: Dim trans As EnvDTE80.Transport = dbg2.Transports.Item("Default")
3: Dim processes As EnvDTE.Processes = dbg2.GetProcesses(trans, "")
4: Dim lvProcesses As New ListView
5: For Each proc As EnvDTE80.Process2 In processes
6: If (proc.Name.EndsWith("w3wp.exe")) Then
7: Dim lvi As New ListViewItem
8: lvi.Tag = proc
9: Dim engineList As String
10: lvi.Text = proc.ProcessID
11: lvi.SubItems.Add(proc.UserName)
12: lvProcesses.Items.Add(lvi)
13: End If
14: Next
To keep a reference to the original EnvDTE80.Process2 object I add the reference to the Tag property of the ListViewItem. Now that I have a ListView populated with all IIS processes, I need to do some check to verify if we have processes available.
1: If lvProcesses.Items.Count = 0 Then
2: Return
3: End If
4:
5: If lvProcesses.Items.Count = 1 Then
6: Dim proc As EnvDTE80.Process2 = lvProcesses.Items(0).Tag
7: proc.Attach2()
8: Return
9: End If
As you can see the code is really simple, if I have no valid worker process, I simply return, but if I have a single IIS worker process available, I’ll attach the debugger to it without requiring user input. If I have more than one worker process available I need the user to select the list of the processes he want to attach to.
1: Dim frm As New Form
2: Dim btn As New Button
3: btn.Text = "OK"
4: btn.DialogResult = DialogResult.OK
5: frm.Controls.Add(btn)
6: frm.Width = 700
7: frm.Text = "Choose IIS worker process to debug"
8: btn.Dock = DockStyle.Bottom
9: frm.Controls.Add(lvProcesses)
10: lvProcesses.Dock = DockStyle.Fill
11: lvProcesses.View = View.Details
12: lvProcesses.Columns.Add("ProcessId", 100, HorizontalAlignment.Left)
13: lvProcesses.Columns.Add("User", 300, HorizontalAlignment.Left)
14: 'lvProcesses.Columns.Add("Type", 300, HorizontalAlignment.Left)
15: lvProcesses.FullRowSelect = True
16:
17: If frm.ShowDialog() = DialogResult.OK Then
18: For Each fitem As ListViewItem In lvProcesses.SelectedItems
19: Dim proc As EnvDTE80.Process2 = fitem.Tag
20: proc.Attach2()
21: Next
22: End If
The code is really simple, because it is used only to create a valid Windows Forms interface to show the ListView with Processes info and an OK Button at the bottom to permit to the user to confirm the selection. Now you can start multiple IIS worker process, press the shortcut assigned to this macro and here is the result.
Figure 1: The list of all available IIS processes
The User Interface is minimal, I show the process Id and the user that is actually running the process; this last information is really important, because I usually use a different user for each different product I’m working to, so if I need to attach to all IIS processes of a certain product, I immediately can identify all IIS processes that are running with that credential and attach the debugger to the right list of processes.
When the user press OK button, I can iterate through all selected items of the ListView, cast the Tag property to EnvDTE80.Process2 and attach the debugger to the process. As you can see I use the overload version of the Attach2() process that accepts no parameter; this permits me to avoid to specify if I want to debug asp.net 2.0 or 4.0 code, and I can let the debugger choose the right one. Remember that you cannot debug at the same time ASP.NET 4.0 and earlier version, so you could not choose two worker process that are running two different version of the framework.
This post shows clearly that Visual Studio Macro are powerful, yet very simple to use and they can save you huge amount of time automating recurring operations.
Alk.
A file with the complete macro can be downloaded from here. (http://www.codewrecks.com/files/attachtoiis.txt)
Tags: Macro, Visual Studio


