Developer Resources:

Customer Quotes:

Introduction

WCF and Flex provide numerous benefits for developing server-side functionality in .NET and implementing rich client applications with Flex/ActionScript. The question of integration between these two technologies comes up quite frequently as developers and business want to leverage the best the frameworks have to offer. This article reviews an approach for integrating Flex client applications with WCF services using WebORB for .NET.

Integration Options - Web Services, AMF, etc.

Flex and .NET integration includes several options including web services, HTTP services and AMF Remoting. Each option has its own pros and cons. Specifically with WCF, the framework on the .NET side includes support for exposing WCF services as SOAP/REST web services. Since Flex has built-in support for SOAP web services, it is possible to integrate the client and the server environments using that approach. It is important to understand though that the integration through web services may have negative impact on application's performance as well as the development timeline (time to market). The impact is caused primarily due to the involved complexity and additional hand-coding the web services approaches may require. As for the performance impact, see the AMF/Remoting vs. Web Services comparison benchmark article.

Based on our experience, the approach which provides the best application's performance and speeds up the development is the one based on AMF Remoting between a Flex client and the WCF services. An example of such integration is an architecture which includes an AMF remoting gateway between a Flex client and the .NET backend. A Flex client uses the RemoteObject API to communicate with the remoting gateway, which brokers requests to the backend WCF services. WebORB for .NET is an example of an AMF remoting gateway with solid, industry-proven track record.

Developing a WCF Service

In this article, you will develop a WCF service hosted in IIS. The service will be exposed as a remoting service which can be consumed by a Flex client using WebORB for .NET. WebORB will handle invocations of the WCF service and delivery of the invocation results back to Flex. A future article will review a similar integration where a WCF service is not hosted in IIS but is running standalone in the WCF's service host.

To get started, follow the example reviewed on the following page to develop a sample WCF service: http://msdn.microsoft.com/en-us/library/ms733766.aspx.

The service you developed should have the following source code:

   1:  using System;
   2:  using System.ServiceModel;
   3:   
   4:  namespace Microsoft.ServiceModel.Samples
   5:  {
   6:   
   7:    [ServiceContract]
   8:    public interface ICalculator
   9:    {
  10:       [OperationContract]
  11:       double Add(double n1, double n2);
  12:       [OperationContract]
  13:       double Subtract(double n1, double n2);
  14:       [OperationContract]
  15:       double Multiply(double n1, double n2);
  16:       [OperationContract]
  17:       double Divide(double n1, double n2);
  18:    }
  19:   
  20:   
  21:    public class CalculatorService : ICalculator
  22:    {
  23:       public double Add(double n1, double n2)
  24:       {
  25:          return n1 + n2;
  26:       }
  27:       public double Subtract(double n1, double n2)
  28:       {
  29:          return n1 - n2;
  30:       }
  31:       public double Multiply(double n1, double n2)
  32:       {
  33:          return n1 * n2;
  34:       }
  35:       public double Divide(double n1, double n2)
  36:       {
  37:          return n1 / n2;
  38:       }
  39:    } 
  40:  }

The configuration file (web.config) for your service and web application should contain the following elements:

   1:  <?xml version="1.0" encoding="utf-8" ?>
   2:  <configuration>
   3:    <system.serviceModel>
   4:      <services>
   5:        <service name="Microsoft.ServiceModel.Samples.CalculatorService">
   6:          <endpoint address=""
   7:                    binding="wsHttpBinding"
   8:                    contract="Microsoft.ServiceModel.Samples.ICalculator" />
   9:        </service>
  10:      </services>
  11:    </system.serviceModel>
  12:  </configuration>

To complete the deploying of the server-side of the application, deploy WebORB into the created ASP.NET application where your WCF service is running. Make sure to include the WebORB management console into the deployment so you can verify the presence of your WCF service. To do that, navigate to "weborb.aspx" in your application, the console should open up. If you use WebORB version 3, select Management and locate an assembly with your WCF code in the services tab. If you use WebORB version 4, you should find your WCF service under the "WCF Services" node in the "Services" section.

Developing Flex Client

Create a Flex Project using Flash Builder as described in the Introduction to Flex with .NET integration article. Replace the contents of the default MXML application with the source code shown below. Also can download and use the full source code listing for the example.

   1:  <?xml version="1.0" encoding="utf-8"?>
   2:  <s:Application xmlns:fx="http://ns.adobe.com/mxml/2009" 
   3:                 xmlns:s="library://ns.adobe.com/flex/spark" 
   4:                 xmlns:mx="library://ns.adobe.com/flex/halo"
   5:                 creationComplete="init()">
   6:    <fx:Script>
   7:      <![CDATA[
   8:        import mx.controls.Alert;
   9:        import mx.rpc.events.FaultEvent;
  10:        import mx.rpc.events.ResultEvent;
  11:        import mx.rpc.remoting.RemoteObject;
  12:        
  13:        [Bindable]
  14:        private var ops:Array = ["+", "-", "*", "/" ];
  15:        private var wcfProxy:RemoteObject;
  16:        
  17:        private function init():void
  18:        {
  19:          wcfProxy = new RemoteObject( "GenericDestination" );
  20:          wcfProxy.source = "Microsoft.ServiceModel.Samples.CalculatorService";
  21:          wcfProxy.addEventListener( ResultEvent.RESULT, gotResult );
  22:          wcfProxy.addEventListener( FaultEvent.FAULT, gotError );
  23:        }
  24:        
  25:        private function calculate():void
  26:        {
  27:          if( opList.selectedLabel == "+" ) 
  28:            wcfProxy.Add( arg1.text as Number, arg2.text as Number );
  29:          else if( opList.selectedLabel == "-" ) 
  30:            wcfProxy.Subtract( arg1.text as Number, arg2.text as Number );
  31:          else if( opList.selectedLabel == "*" ) 
  32:            wcfProxy.Multiply( arg1.text as Number, arg2.text as Number );
  33:          else
  34:            wcfProxy.Divide( arg1.text as Number, arg2.text as Number );
  35:        }
  36:        
  37:        private function gotResult( event:ResultEvent ):void
  38:        {
  39:          result.text = event.result.toString();
  40:        }
  41:        
  42:        private function gotError( event:FaultEvent ):void
  43:        {
  44:          Alert.show( "Server reported an error - " + event.fault.faultDetail );
  45:        }
  46:      ]]>
  47:    </fx:Script>
  48:    <s:Panel y="10" height="258" width="405" x="10" title="WCF Calculator">
  49:      <mx:Form left="20" right="20" top="20">
  50:        <mx:FormItem label="Argument 1">
  51:          <s:TextInput id="arg1" width="100%"/>
  52:        </mx:FormItem>
  53:        <mx:FormItem label="Operator">
  54:          <mx:ComboBox id="opList" editable="false" width="100%" dataProvider="{ops}" />
  55:        </mx:FormItem>
  56:        <mx:FormItem label="Argument 2">
  57:          <s:TextInput id="arg2" width="100%"/>
  58:        </mx:FormItem>
  59:      </mx:Form>
  60:      <s:Button x="20" y="149" label="Calculate" click="calculate()"/>
  61:      <s:Label x="21" y="183" text="Result:"/>
  62:      <s:Label x="69" y="178" id="result" />
  63:    </s:Panel>
  64:  </s:Application>

The Flex client uses the AMF Remoting (RemoteObject) API to invoke the WCF service operations. This is not different than invoking regular .NET methods from Flex. On the server-side, when an invocation of a WCF operation takes place, the handling will vary depending on the version of WebORB installed:

With the version 3 of WebORB, the call processing will be the same as for a regular .NET assembly/class. However, the version 4 of the product automatically detects that the target service is a WCF service and includes special handling logic to accomodate WCF invocation handling pipeline. In that case, most of the WCF operation/class annotations will be included in the processing.

Serialization of invocation result values is handled the same way as with the non-WCF classes. WebORB serializes return values into AMF and delivers response back to Flex.