Task 5: Create a Tracking ProfileĀ
Tracking profiles are used to control the type of tracking information that the Windows Workflow Foundation runtime engine generates. By default, tracking information is saved for every workflow and activity event when you use a default profile.
In this task, you create a custom tracking profile that will track all the workflow events and activity events, but only for the CodeActivity activities. Any other activities in the workflow will not generate any tracking information when this profile is used.
Note |
---|
Although you are encouraged to follow the exercises in a linear manner, it is not required. You can start this exercise by opening the sample project and proceeding to the steps in the following section. |
Creating the Profile
Follow these steps to import the required namespaces and create the tracking profile.
To import the namespaces
In the Program source file, add the following directives to import the types that you must have for tracking profiles.
Imports System.IO Imports System.Globalization Imports System.Workflow.ComponentModel Imports System.Workflow.Activities
using System.IO; using System.Globalization; using System.Workflow.ComponentModel; using System.Workflow.Activities;
To create the tracking profile
In the Program class of your project, create a static method named CreateTrackingProfile.
Private Shared Sub CreateTrackingProfile() End Sub
static void CreateTrackingProfile() { }
In the CreateTrackingProfile method that you created in step 1, create a TrackingProfile object named profile and an ActivityTrackPoint object named trackPoint. Additionally, set the Version property of the TrackingProfile object equal to a new instance of a Version object passing the string "1.0.0.0" as a parameter to the constructor.
Dim profile As TrackingProfile = New TrackingProfile() Dim trackPoint As ActivityTrackPoint = New ActivityTrackPoint() profile.Version = New Version("1.0.0.0")
TrackingProfile profile = new TrackingProfile(); ActivityTrackPoint trackPoint = new ActivityTrackPoint(); profile.Version = new Version("1.0.0.0");
Create an ActivityTrackingLocation object named location, passing in the Type of the CodeActivity activity as a parameter to the constructor.
' track CodeActivity activities only Dim location As ActivityTrackingLocation = _ New ActivityTrackingLocation(GetType(CodeActivity))
// track CodeActivity activities only ActivityTrackingLocation location = new ActivityTrackingLocation (typeof(CodeActivity));
Enumerate through the values in the ActivityExecutionStatus enumerated data type, and add those values to the ExecutionStatusEvents collection that is defined in the ActivityTrackingLocation object.
' add all activity tracking events For Each s As ActivityExecutionStatus In System.Enum.GetValues _ (GetType(ActivityExecutionStatus)) location.ExecutionStatusEvents.Add(s) Next s
// add all activity tracking events foreach (ActivityExecutionStatus s in Enum.GetValues(typeof(ActivityExecutionStatus))) { location.ExecutionStatusEvents.Add(s); }
Add the ActivityTrackingLocation object to the MatchingLocations collection that is defined in the ActivityTrackPoint object.
Add the ActivityTrackPoint object to the ActivityTrackPoints collection that is defined in the TrackingProfile object.
trackPoint.MatchingLocations.Add(location) profile.ActivityTrackPoints.Add(trackPoint)
trackPoint.MatchingLocations.Add(location); profile.ActivityTrackPoints.Add(trackPoint);
Create a new WorkflowTrackPoint object named wtp and a WorkflowTrackingLocation object named wtl.
Dim wtp As WorkflowTrackPoint = New WorkflowTrackPoint() Dim wtl As WorkflowTrackingLocation = New WorkflowTrackingLocation()
WorkflowTrackPoint wtp = new WorkflowTrackPoint(); WorkflowTrackingLocation wtl = new WorkflowTrackingLocation();
Enumerate through the TrackingWorkflowEvent enumerated data type, and add each value to the Events collection that is defined in the WorkflowTrackingLocation object.
' add all workflow tracking events For Each s As TrackingWorkflowEvent In System.Enum.GetValues( _ GetType(TrackingWorkflowEvent)) wtl.Events.Add(s) Next s
// add all workflow tracking events foreach (TrackingWorkflowEvent s in Enum.GetValues(typeof(TrackingWorkflowEvent))) { wtl.Events.Add(s); }
Set the MatchingLocation property that is defined in the WorkflowTrackPoint object to the WorkflowTrackingLocation object.
Add the WorkflowTrackPoint object to the WorkflowTrackPoints collection that is defined in the TrackingProfile object.
wtp.MatchingLocation = wtl profile.WorkflowTrackPoints.Add(wtp)
wtp.MatchingLocation = wtl; profile.WorkflowTrackPoints.Add(wtp);
Create a new TrackingProfileSerializer object named serializer and a StringWriter object named writer.
' serialize tracking profile and save to SQL Dim serializer As TrackingProfileSerializer = New TrackingProfileSerializer() Dim writer As StringWriter = New StringWriter(New StringBuilder(), _ CultureInfo.InvariantCulture)
// serialize tracking profile and save to SQL TrackingProfileSerializer serializer = new TrackingProfileSerializer(); StringWriter writer = new StringWriter(new StringBuilder(), CultureInfo.InvariantCulture);
Serialize the TrackingProfile object by calling the Serialize method that is defined in the TrackingProfileSerializer class.
Pass the StringWriter and TrackingProfile objects as parameters to that method.
serializer.Serialize(writer, profile)
serializer.Serialize(writer, profile);
Call the InsertTrackingProfile method, passing writer.ToString() as a parameter to that method.
Note You create the InsertTrackingProfile method in the next procedure.
InsertTrackingProfile(writer.ToString())
InsertTrackingProfile(writer.ToString());
In the Main method of the Program class, call the CreateTrackingProfile method you just created. This method should be called prior to the creation of the WorkflowRuntime object.
CreateTrackingProfile()
CreateTrackingProfile();
Saving the Tracking Profile to a Database
To save the tracking profile to a SQL database
In the Program class of your project, create a new static method named InsertTrackingProfile that takes a String named profile as a parameter.
Private Shared Sub InsertTrackingProfile(ByVal profile As String) End Sub
static void InsertTrackingProfile(string profile) { }
In the InsertTrackingProfile method, create a new SqlCommand object named cmd.
Dim cmd As SqlCommand = New SqlCommand()
SqlCommand cmd = new SqlCommand();
Using the SqlCommand object that you created in the previous step, set the CommandType property to CommandType.StoredProcedure, set the CommandText property to "dbo.UpdateTrackingProfile".
Create a new SqlConnection object, passing Program.connectionString as a parameter to the constructor, and assign this object to the Connection property that is defined in the SqlCommand object.
cmd.CommandType = CommandType.StoredProcedure cmd.CommandText = "dbo.UpdateTrackingProfile" cmd.Connection = New SqlConnection(Program.connectionString)
cmd.CommandType = CommandType.StoredProcedure; cmd.CommandText = "dbo.UpdateTrackingProfile"; cmd.Connection = new SqlConnection(Program.connectionString);
Create a new try block, and put the code for steps 6 through 15 in that block.
Create a new SqlParameter object named typFullName, and set its properties as outlined in the following table.
Property Name Property Value ParameterName
"@TypeFullName"
SqlDbType
SqlDbType.NVarChar
SqlValue
typeof(Microsoft.Samples.Workflow.Tutorials.Hosting.HostingWorkflows).ToString();
Add the SqlParameter object to the Parameters collection that is defined in the SqlCommand object.
Your code for the typFullName object will appear similar to the following.
Dim typFullName As SqlParameter = New SqlParameter() typFullName.ParameterName = "@TypeFullName" typFullName.SqlDbType = SqlDbType.NVarChar typFullName.SqlValue = GetType(HostingWorkflows).ToString() cmd.Parameters.Add(typFullName)
SqlParameter typFullName = new SqlParameter(); typFullName.ParameterName = "@TypeFullName"; typFullName.SqlDbType = SqlDbType.NVarChar; typFullName.SqlValue = typeof(HostingWorkflows).ToString(); cmd.Parameters.Add(typFullName);
Create a new SqlParameter object named assemblyFullName, and set its properties as outlined in the following table.
Property Name Property Value ParameterName
"@AssemblyFullName"
SqlDbType
SqlDbType.NVarChar
SqlValue
typeof(Microsoft.Samples.Workflow.Tutorials.Hosting.HostingWorkflows).Assembly.FullName
Add the SqlParameter object to the Parameters collection that is defined in the SqlCommand object.
Your code for the assemblyFullName object will appear similar to the following.
Dim assemblyFullName As SqlParameter = New SqlParameter() assemblyFullName.ParameterName = "@AssemblyFullName" assemblyFullName.SqlDbType = SqlDbType.NVarChar assemblyFullName.SqlValue = GetType(HostingWorkflows).Assembly.FullName cmd.Parameters.Add(assemblyFullName)
SqlParameter assemblyFullName = new SqlParameter(); assemblyFullName.ParameterName = "@AssemblyFullName"; assemblyFullName.SqlDbType = SqlDbType.NVarChar; assemblyFullName.SqlValue = typeof(HostingWorkflows).Assembly.FullName; cmd.Parameters.Add(assemblyFullName);
Create a new SqlParameter object named versionId, and set its properties as outlined in the following table.
Property Name Property Value ParameterName
"@Version"
SqlDbType
SqlDbType.VarChar
SqlValue
"1.0.0.0"
Add the SqlParameter object to the Parameters collection that is defined in the SqlCommand object.
Your code for the versionId object will appear similar to the following.
Dim versionId As SqlParameter = New SqlParameter() versionId.ParameterName = "@Version" versionId.SqlDbType = SqlDbType.VarChar versionId.SqlValue = "1.0.0.0" cmd.Parameters.Add(versionId)
SqlParameter versionId = new SqlParameter(); versionId.ParameterName = "@Version"; versionId.SqlDbType = SqlDbType.VarChar; versionId.SqlValue = "1.0.0.0"; cmd.Parameters.Add(versionId);
Create a new SqlParameter object named trackingProfile, and set its properties as outlined in the following table.
Property Name Property Value ParameterName
"@TrackingProfileXml"
SqlDbType
SqlDbType.NVarChar
SqlValue
profile
Add the SqlParameter to the Parameters collection that is defined in the SqlCommand object.
Your code for the trackingProfile object will appear similar to the following.
Dim trackingProfile As SqlParameter = New SqlParameter() trackingProfile.ParameterName = "@TrackingProfileXml" trackingProfile.SqlDbType = SqlDbType.NVarChar trackingProfile.SqlValue = profile cmd.Parameters.Add(trackingProfile)
SqlParameter trackingProfile = new SqlParameter(); trackingProfile.ParameterName = "@TrackingProfileXml"; trackingProfile.SqlDbType = SqlDbType.NVarChar; trackingProfile.SqlValue = profile; cmd.Parameters.Add(trackingProfile);
Call the Open method that is defined in the Connection property of the SqlCommand object.
Call the ExecuteNonQuery method that is defined in the SqlCommand object to execute the stored procedure and subsequently save your tracking profile.
cmd.Connection.Open() cmd.ExecuteNonQuery()
cmd.Connection.Open(); cmd.ExecuteNonQuery();
Create a new catch block for the SqlException exception following the try block that you created in steps 5 through 15.
In the catch block, use the WriteLine method to display the Message property that is defined in the SqlException object.
Additionally, add a message explaining the steps that are required to update the tracking profile with a new version number whenever the tracking profile is changed.
Catch e As SqlException Console.WriteLine(e.Message) Console.WriteLine( _ "The Tracking Profile was not inserted. " & _ "If you want to add a new Tracking Profile, modify the version " & _ "string in the profile by specifying a higher version number.") Return
catch (SqlException e) { Console.WriteLine(e.Message); Console.WriteLine("The Tracking Profile was not inserted. " + "if you want to add a new Tracking Profile, modify the version " + "string in the profile by specifying a higher version number."); return; }
Create a finally block, and call the Close method followed by the Dispose method defined in the Connection property of the SqlCommand object.
Finally If (Not Nothing Is cmd) AndAlso (Not Nothing Is cmd.Connection) _ AndAlso (ConnectionState.Closed <> cmd.Connection.State) Then cmd.Connection.Close() cmd.Connection.Dispose() End If End Try
finally { if ((null != cmd) && (null != cmd.Connection) && (ConnectionState.Closed != cmd.Connection.State)) { cmd.Connection.Close(); cmd.Connection.Dispose(); } }
Build your project and run it.
Your output will appear similar to the following illustration.
Compiling the Code
Click Start, point to Programs, point to Microsoft .NET Framework SDK v2.0, and then click SDK Command Prompt.
Go to the source directory of the tutorial.
At the command prompt, type MSBUILD to build the project.
For a completed tutorial, see Completed Windows Workflow Foundation Runtime Hosting Tutorial.
See Also
Reference
System.Workflow.Runtime.Tracking
TrackingProfile
ActivityTrackPoint
ActivityExecutionStatus
ActivityTrackingLocation
WorkflowTrackPoint
WorkflowTrackingLocation
TrackingProfileSerializer
Concepts
Creating Custom Tracking Services
Creating and Using Tracking Profiles
Other Resources
Simple Tracking Example
Query Using SQLTrackingService
Tracking Using User Track Points
EventArgs Tracking Sample
ConsoleTrackingService Sample
Send comments about this topic to Microsoft.