Friday, March 16, 2012

WCF Duplex Service Hosted in A Console Application

Create Service Contracts

 [ServiceContract(Namespace = "Silverlight", CallbackContract = typeof(IDuplexClient))]
    public interface IDuplexService
    {
        [OperationContract]
        void Order(string name, int quantity);
    }

    [ServiceContract]
    public interface IDuplexClient
    {
        [OperationContract(IsOneWay = true)]
        void Receive(Order order);
    }


    [ServiceContract]
    public interface IPolicyRetriever
    {
        [OperationContract, WebGet(UriTemplate = "/clientaccesspolicy.xml")]
        Stream GetSilverlightPolicy();
        [OperationContract, WebGet(UriTemplate = "/crossdomain.xml")]
        Stream GetFlashPolicy();
    }



Implement Service Contracts:
  public class OrderService : IDuplexService,IPolicyRetriever
    {
        public static Dictionary Clients = new Dictionary();


        IDuplexClient client;
        string orderName;
        int orderQuantity;

        public void Order(string name, int quantity)
        {
            // Grab the client callback channel.
            client = OperationContext.Current.GetCallbackChannel();
            orderName = name;
            orderQuantity = quantity;

            Clients[name] = client;

            // Pretend service is processing and will call client back in 5 seconds.
            using (Timer timer = new Timer(new TimerCallback(CallClient), null, 5000, 5000))
            {
                Thread.Sleep(11000);
            }
        }



        bool processed = false;

        private void CallClient(object o)
        {
            Order order = new Order();
            order.Payload = new List();

            // Process order.
            if (processed)
            {
                // Pretend service is fulfilling the order.
                while (orderQuantity-- > 0)
                {
                    order.Payload.Add(orderName + orderQuantity);
                }

                order.Status = OrderStatus.Completed;

            }
            else
            {
                // Pretend service is processing payment.
                order.Status = OrderStatus.Processing;
                processed = true;
            }

            // Call client back.
            client.Receive(order);

        }


        Stream StringToStream(string result)
        {
            WebOperationContext.Current.OutgoingResponse.ContentType = "application/xml";
            return new MemoryStream(Encoding.UTF8.GetBytes(result));
        }

        public Stream GetSilverlightPolicy()
        {
            string result = @"

   
       
           
               
           

           
               
           

       

   
";
            return StringToStream(result);
        }
        public Stream GetFlashPolicy()
        {
            string result = @"


   
";
            return StringToStream(result);
        }

    }


Running the service:

 static void Main(string[] args)
        {
            //Creating a new ServiceHost instance with two base addresses: one for the http and second for the net.tcp
            using (ServiceHost sh = new ServiceHost(typeof(OrderService), new Uri("http://localhost:72/Service")))
            {
                //Adding the endpoints to the ServiceHost
                //sh.AddServiceEndpoint(typeof(IDuplexService), new NetTcpBinding(), "");
                sh.AddServiceEndpoint(typeof(IDuplexService), new PollingDuplexHttpBinding(), "");
                sh.AddServiceEndpoint(typeof(IPolicyRetriever), new WebHttpBinding(), "http://localhost:72/").Behaviors.Add(new WebHttpBehavior());

                //Creating a new Service Behavior
                ServiceMetadataBehavior smb = new ServiceMetadataBehavior();
                smb.HttpGetEnabled = true;
                sh.Description.Behaviors.Add(smb);

                //Opening the ServiceHost for incoming connections
                sh.Open();

                System.Console.WriteLine("Waiting for connections...");
                System.Console.ReadLine();

                //Close opened ServiceHost object
                sh.Close();
            }
        }



before you actually run the service you will have register the url of service to ACL.
on vista and win 2008

C:\Windows\system32>netsh http add urlacl url=http://+:72/Service/ user=shoaibpc-3


use httpcfg for winxp
 

No comments: