From our current poll on your opinion about Flash Remoting with CFForm, it is clear that most of our readers are excited about it. There are others, however, that either find it too complex or do not know what Remoting is.
I will try to help both groups by explaining what Remoting is and how it can be used.
From our current poll on your opinion about Flash Remoting with CFForm, it is clear that most of our readers are excited about it. There are others, however, that either find it too complex or do not know what Remoting is.
I will try to help both groups by explaining what Remoting is and how it can be used.
Flash Remoting is a great Macromedia technology, which has always been on the back, nobody really paying too much attention to it. In Macromedia’s words, “Flash Remoting MX is an application server gateway that provides a network communications channel between Flash applications and remote services.” There is a distinction between the server (the gateway) and the client (the Flash components), but we’ll generalize it as simply “Flash Remoting”.
Basically, it provides a very easy to use method to send data back and forth from Flash to the server. The server can be ColdFusion, which comes with Remoting out of the box, .NET or Java, for which you would need to buy a license, or PHP, by using AMFPHP. I will focus the discussion on the ColdFusion version because I will then talk about Remoting and CFForms.
What it really does is to serialize Flash objects, send them to the server, deserialize them and give them to CF (or the others) in a way they can be natively consumed. It does the same thing the other way around, serializing CF objects, sending them to Flash and deserializing them on the client as Flash Objects. But the benefits do not stop there, as the format used to send the messages, called “AMF” is binary, making the messages much smaller than plain xml. This gives it a performance advantage over Web Services.
For anyone who had to deal with parsing xml on the client, for example, this is bliss. You have a CF array? No problem, send that to Flash, which will see it as nothing more than another array. What about a query, so that we don’t even have to massage the data coming from the database? Sure, Flash will get is as a RecordSet. Mostly everything can be sent back and forth. Is it important to note that what you get on either side is not the same “instance” of the object you are sending. For simple data types this does not really matter, but what matters is that on either side you will have to use the methods and properties native to the language, be it Flash (ActionScript) or CF (CFML). This means that even if you manage to send a complex object (most of the time the gateway won’t allow it), this object will get serialized into a simpler object with only properties, even if you original object had methods. For example, if you send a query from ColdFusion, Flash will see it as a RecordSet. In CF, you have some methods to deal with queries, such as queryAddRow(). That method will not exist in Flash, instead, you will need to find the corresponding method in Flash, such as addItem(). This may seem obvious but it is a really common mistake, mostly when it comes to user-defined classes. No matter how many functions your cfc has, it you send an instance of that cfc to Flash, it will only see an anonymous object with public properties (this.myVariable) and no functions (except for those functions that any Object in ActionScript has).
Each application server has a different implementation of Flash Remoting, as you might expect. But there are also different ways of using remoting within them. With ColdFusion, my preferred method is to use only CFCs. It really makes a very clean implementation: when you need something from the server, you call a CFC function, that will return an object (or void for that matter) of the type specified in the function definition. If I have, for example, a CFC with a function called getCustomers(), I would call myService.getCustomers() in AS code. This is very intuitive.
There are big changes between version 1 and version 2 of remoting, so make sure you are looking at the latest documentation . There are also, just to make it easy, several ways of establishing a connection, and making the call.
As of the version 2.0, the preferred method is by using the Service class. This is an example from MM documentation:
custService = new Service("http://localhost/flashservices/gateway", null, "customerData", null, null); then call a function on the customerData cfc: var pc:PendingCall = custService.getCategories(); // get all categories //define what to do with the call pc.responder = new RelayResponder(this, "onCategoryData", "onCategoryFault" );
where the last two parameters specify the functions to call when the service sends a response or it faults.
This all looks good, but having to create all those objects by “new” makes it a problem if we want to use it in flash forms. Unfortunately, the only workaround (that I have found) is to use the NetServices class, which is deprecated. As always, we are playing with fire when it comes to cfform and the future support of any of these undocumented techniques.
In the cfform, we must first create a connection by:
mx.remoting.NetServices.setDefaultGatewayUrl( "http://www.example.com/flashservices/gateway"); var connection:mx.remoting.Connection = mx.remoting.NetServices.createGatewayConnection();
or simply:
var connection:mx.remoting.Connection = mx.remoting.NetServices.createGatewayConnection( "http://www.example.com/flashservices/gateway/");
After that we can get an instance of our service, so that we can call several methods on it:
var myService:mx.remoting.NetServiceProxy = connection.getService("path.to.my.cfc", responseHandler );
responsesHandler is a simple object declared as
var responseHandler = {}; responseHandler.onResult = function( results: Object ):Void { } responseHandler.onStatus = function( stat: Object ):Void { }
Each of those functions will handle the results of the remoting call, the first one on success and the second on error.
If we want to call several different methods in our CFC and do different things with the results, then we can declare the handling functions as
responseHandler.myFunction_Result = function( results: Object ):Void { } responseHandler.myFunction_Status = function( status: Object ):Void { }
and then just make the call:
myService.myFunction(parameters);
It really doesn’t take more than a few lines of code to get Remoting up and running. The most difficult part is knowing how to send and receive complex data. I will cover that in the next part of this tutorial, so stay tuned.
But before I go, I wanted to give some information about Remoting and installation issues. ColdFusion comes with remoting out of the box. If everything is properly configured, you shouldn’t have to do anything to get it running. The gateway sits at
http://www.example.com/flashservices/gateway/
However, if you believe that it is not properly installed, you are running IIS and you have access to it, you can check whether there is a virtual directory called JRunScripts in your site definition at IIS. If it is not there, you must create it, pointing it to something like C:\CFusionMX7\runtime\lib\wsconfig\1 (it will be different if you have CF installed in a different directory or if you are running the J2EE version of CF) and give it script and executables permissions. For more info, see this technote: ColdFusion MX: Recommended configuration of multihomed Microsoft IIS web servers