Click here to Skip to main content
15,885,869 members
Articles / Programming Languages / C#

Service Bus Architecture based on WCF (3): Build your ESB

Rate me:
Please Sign up or sign in to vote.
4.87/5 (18 votes)
10 Feb 2011CPOL4 min read 76.8K   8.3K   52  
Service Bus Architecture based on WCF (3): build your ESB
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Workflow.Runtime;
using System.Workflow.Activities;
using System.Reflection;
using System.Workflow.Runtime.Hosting;
using System.Collections.ObjectModel;
using Trilobita.SAOT.Object;

namespace Trilobita.SAOT.Process
{
    public class ProcessManager
    {
        #region Properties
        private WorkflowRuntime Runtime;
        private ISAOTDataService MyDataService;
        private Assembly WorkflowsAssembly = null;
        private string AssemblyName = string.Empty;

        public static string DefaultAssemblyName { get; set; }
        #endregion

        #region Static Methods
        
        private static Dictionary<string, ProcessManager> ProcessManagers = new Dictionary<string, ProcessManager>();
        public static ProcessManager Register(ISAOTDataService externaldataservice, string assemblyName) 
        {
            ProcessManager manager = ProcessManagers[assemblyName.ToUpper().Trim()];
            if (manager == null)
            {
                manager = new ProcessManager(externaldataservice, assemblyName);
                ProcessManagers.Add(assemblyName.ToUpper().Trim(), manager);
            }
            return manager;
        }
        public static ProcessManager DefaulProcessManager
        {
            get
            {
                return ProcessManagers[DefaultAssemblyName.ToUpper().Trim()];
            }
        }
        public static ProcessManager GetProcessManager(string assesmblyName)
        {
            return ProcessManagers[assesmblyName.ToUpper().Trim()];
        }
        #endregion

        #region Constructor
        /// <summary>
        /// launch runtime, load external data exchange service and load target workflow assembly
        /// </summary>
        /// <param name="externaldataservice"></param>
        /// <param name="assemblyName"></param>
        private ProcessManager(ISAOTDataService externaldataservice, string assemblyName)
        {
            Runtime = new WorkflowRuntime();
            //dataexchange service
            MyDataService = externaldataservice;
            ExternalDataExchangeService dataexchangeService = new ExternalDataExchangeService();
            Runtime.AddService(dataexchangeService);
            dataexchangeService.AddService(MyDataService);

            Runtime.StartRuntime();
            WorkflowsAssembly = Assembly.Load(AssemblyName);
        }
        /// <summary>
        /// load additonal persistence service
        /// </summary>
        /// <param name="externaldataservice"></param>
        /// <param name="assemblyName"></param>
        /// <param name="persistenceconnstring"></param>
        public ProcessManager(ISAOTDataService externaldataservice, string assemblyName,string persistenceconnstring)
            :this(externaldataservice,assemblyName)
        {
            SqlWorkflowPersistenceService persistence = new SqlWorkflowPersistenceService
                (persistenceconnstring, true,TimeSpan.MaxValue, new TimeSpan(0, 2, 0));
            Runtime.AddService(persistence);
        }
        #endregion

        #region Methods
        /// <summary>
        /// start a new workflow
        /// </summary>
        /// <param name="workflow"></param>
        /// <param name="paramters"></param>
        /// <returns></returns>
        public Guid CreateWorkflow(string workflow,Dictionary<string, object> paramters)
        {
            Type workflowType = WorkflowsAssembly.GetType(workflow);
            if (workflowType == null) return Guid.Empty;
            WorkflowInstance instance = Runtime.CreateWorkflow(workflowType, paramters);
            instance.Start();
            return instance.InstanceId;
        }
        /// <summary>
        /// get one process's statemachine
        /// </summary>
        /// <param name="guid"></param>
        /// <returns></returns>
        public StateMachineWorkflowInstance GetState(Guid guid)
        {
            StateMachineWorkflowInstance state = new StateMachineWorkflowInstance(Runtime, guid);
            while(state.CurrentState==null){System.Threading.Thread.Sleep(200);}
            return state;
        }
        /// <summary>
        /// get one process's current state
        /// </summary>
        /// <param name="guid"></param>
        /// <returns></returns>
        public string GetStateName(Guid guid)
        {
            return new StateMachineWorkflowInstance(Runtime, guid).CurrentStateName;
        }
        /// <summary>
        /// get available event of give process
        /// </summary>
        /// <param name="guid"></param>
        /// <returns></returns>
        public WorkflowEventInformation[] GetAvailableEvents(Guid guid)
        {
            List<WorkflowEventInformation> events = new List<WorkflowEventInformation>();
            StateMachineWorkflowInstance state = this.GetState(guid);
            WorkflowInstance instance = state.WorkflowInstance;
            ReadOnlyCollection<WorkflowQueueInfo> subActivities = instance.GetWorkflowQueueData();
            Collection<string> MessagesAllowed = new Collection<string>();
            foreach (WorkflowQueueInfo queueInfo in subActivities)
            {
                EventQueueName queuename = queueInfo.QueueName as EventQueueName;
                if (queuename != null)
                {
                    Type type = this.MyDataService.GetType();
                    System.Reflection.MemberInfo info = type.GetMember(queuename.MethodName)[0];
                    object[] atts = info.GetCustomAttributes(typeof(WFEventAttribute), false);
                    WFEventAttribute att = atts[0] as WFEventAttribute;
                    events.Add(new WorkflowEventInformation()
                    {
                        MethodName = queuename.MethodName,
                        Title = (att == null ? queuename.MethodName : att.Title),
                        Description = (att == null ? "" : att.Description),
                        InstanceID = guid,
                        Type = "Event"
                    });
                }
            }
            return events.ToArray();
        }
                    
        public void RaiseEvent(WorkflowEventInformation wfevent,WorkflowParameter parameter)
        {
            this.MyDataService.RaiseEvent(wfevent, parameter);
        }
        #endregion
    }
}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
China China
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions