Hey guys, I just wanted to verify what I'm doing is correct. It came to our attention that a Windows Service had a pretty serious memory leak. I was able to track it down to how Workflow was being called. I reworked it a bit to stop the memory leak, but I wanted to validate that the code is doing what I think it is. Note I do not know the first thing about Workflow, so I'm coming to you.
Basically, the code was executing the Workflow on a thread, but was not removing the handler to WorkflowRuntime.Terminated. I am trying to ensure that the Workflow is executed asynchronously. Here are the relevant portions of code:
Checking to ensure there is only once instance of the WorkflowRuntime:
private static void _CheckRuntimeInstance()
{
lock (_padlock)
{
if (_wfRuntime == null)
{
_wfRuntime = new WorkflowRuntime();
ManualWorkflowSchedulerService schedulerService = new ManualWorkflowSchedulerService();
_wfRuntime.AddService(schedulerService);
_wfRuntime.StartRuntime();
}
}
}
Inside a static method, creating the specific WorkflowInstance to run:
_CheckRuntimeInstance();
// create the instance
WorkflowInstance instance = _wfRuntime.CreateWorkflow(typeof(WorkflowType),parameters);
instance.Start();
Guid instanceId = instance.InstanceId;
ThreadPool.QueueUserWorkItem(CallbackMethod, instanceId);
Thread callback method:
private static void DeviceLocationAssignmentCallback(Object state)
{
Guid instanceId = (Guid)state;
EventHandler<WorkflowTerminatedEventArgs> workflowTerminatedHandler = null;
EventHandler<WorkflowCompletedEventArgs> workflowCompletedHandler = null;
workflowTerminatedHandler = delegate(object sender, WorkflowTerminatedEventArgs e)
{
if (instanceId == e.WorkflowInstance.InstanceId)
{
// Remove event registration.
_wfRuntime.WorkflowTerminated -= workflowTerminatedHandler;
_wfRuntime.WorkflowCompleted -= workflowCompletedHandler;
if (e.Exception != null)
{
// Log error.
}
}
};
_wfRuntime.WorkflowTerminated += workflowTerminatedHandler;
workflowCompletedHandler = delegate(object sender, WorkflowCompletedEventArgs e)
{
if (instanceId == e.WorkflowInstance.InstanceId)
{
// Remove event registrations.
_wfRuntime.WorkflowTerminated -= workflowTerminatedHandler;
_wfRuntime.WorkflowCompleted -= workflowCompletedHandler;
}
};
_wfRuntime.WorkflowCompleted += workflowCompletedHandler;
_wfRuntime.GetService<ManualWorkflowSchedulerService>().RunWorkflow(instanceId);
}
EDIT: Changed the title of the post to get more views.