Click here to Skip to main content
15,892,537 members
Articles / Programming Languages / C# 4.0

Dynamic Send Activity in WF4

Rate me:
Please Sign up or sign in to vote.
4.43/5 (6 votes)
30 May 2010CPOL14 min read 62.4K   988   29  
This article describes a design, implementation and usage of the custom Dynamic Send Activity in the .Net WF4 Technology.
//*****************************************************************************
//    Description.....WF4 Dynamic Send Activity
//                                
//    Author..........Roman Kiss, rkiss@pathcom.com
//    Copyright © 2009 ATZ Consulting Inc. (see included license.rtf file)         
//                        
//    Date Created:    05/05/10
//
//    Date        Modified By     Description
//-----------------------------------------------------------------------------
//    05/05/10    Roman Kiss     Initial Revision
//
//*****************************************************************************
//
#region Namespaces
using System;
using System.Activities;
using System.Activities.Presentation;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.ServiceModel;
using System.ServiceModel.Activities;
using System.ServiceModel.Channels;
using System.ServiceModel.Configuration;
using System.Windows;
using System.Windows.Markup;
using System.Xml.Linq;

#endregion

namespace RKiss.Activities.DynamicSend
{
    [ContentProperty("Body")]
    [DesignTimeVisible(false)]
    public sealed class SendScope : NativeActivity, IXamlLoadErrorService
    {
        [Category("Input")]
        [DefaultValue((string)null)]
        public InArgument<dynamic> Binding { get; set; }

        [Category("Input")]
        [DefaultValue((string)null)]
        public InArgument<dynamic> Headers { get; set; }
 
        [Browsable(false)]
        public Send Body { get; set; }

        protected override void CacheMetadata(NativeActivityMetadata metadata)
        {
            if (this.Body == null)
                metadata.AddValidationError("Missing a Send Activity in the scope");

            if (this.Body != null && this.Body.Endpoint == null)
                this.Body.Endpoint = new Endpoint() { Binding = new BasicHttpBinding(), AddressUri = new Uri("http://localhost/Fake") };
 

            Collection<RuntimeArgument> arguments = new Collection<RuntimeArgument>();
            if (this.Binding != null)
            {
                RuntimeArgument argumentBinding = new RuntimeArgument("Binding", typeof(object), ArgumentDirection.In, true);
                metadata.Bind(this.Binding, argumentBinding);
                arguments.Add(argumentBinding);
            }

            if (this.Headers != null)
            {
                RuntimeArgument argumentHeaders = new RuntimeArgument("Headers", typeof(object), ArgumentDirection.In, true);
                metadata.Bind(this.Headers, argumentHeaders);
                arguments.Add(argumentHeaders);
            }

            metadata.SetArgumentsCollection(arguments);
            metadata.AddChild(Body);
        }

        protected override void Execute(NativeActivityContext context)
        {
            // inject headers
            if (this.Headers != null)
            {
                context.Properties.Add("MessageInspector", new SendMessageInspector() { MessageHeaders = this.Headers.Get(context) });
            }

            // update binding
            if (this.Binding != null)
            {
                dynamic dynBinding = this.Binding.Get(context);

                if (dynBinding is XElement || dynBinding is string)
                {
                    XElement bindingElement = dynBinding is XElement ? dynBinding : XElement.Parse(dynBinding);
                    var bs = LibHelper.DeserializeSection<BindingsSection>(string.Concat("<bindings>", bindingElement.ToString(), "</bindings>"));
                    var bce = bs.BindingCollections.Find(b => b.BindingName == bindingElement.Name.LocalName);

                    Binding binding = Activator.CreateInstance(bce.BindingType) as Binding;
                    if (bce.ConfiguredBindings.Count == 1)
                        bce.ConfiguredBindings[0].ApplyConfiguration(binding);

                    this.Body.Endpoint.Binding = binding;
                }             
                else 
                {
                    this.Body.Endpoint.Binding = dynBinding;
                }              
            }

            context.ScheduleActivity(Body, OnFaulted);
        }

        private void OnFaulted(NativeActivityFaultContext faultContext, Exception propagatedException, ActivityInstance propagatedFrom)
        {
        }

        public void ShowXamlLoadErrors(IList<XamlLoadErrorInfo> errors)
        {
            throw new NotImplementedException();
        }
    }


    public class SendScopeFactory : IActivityTemplateFactory
    {
        public Activity Create(DependencyObject target)
        {
            return new SendScope()
                 {
                     DisplayName = "SendScope",
                     Body = new Send()
                     {
                         Action = "*",
                         OperationName = "ProcessMessage",
                         ServiceContractName = "IGenericContract",
                         Endpoint = new Endpoint()
                         { 
                             Binding = new BasicHttpBinding()                            
                         }
                     }
                 };
        }
    }
}




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
Software Developer (Senior)
United States United States
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions