/customers/iconara.net/iconara.net/httpd.www/blog/wp-content/plugins/wp-super-cache/wp-cache-phase1.php Iconara » Flex WebServices, problem with <any/>

Flex WebServices, problem with <any/>

A while back I wrote about using Flex with Amazon WebServices and the problems I had using Flex’ WebService component. Now I’ve tried working with web services in Flex again and discovered new problems having to do with Flex’ serialization of the request when the data type of a parameter is <any/>.

A quick digression into .NET

I’ve never worked with .NET before, but when new client wanted some way to change the content of the website I was building and their server only ran ASP.NET I thought I might give it a go. How hard could it be?

Not very hard it turned out. Writing a web service backend in C#/ASP.NET is really simple. The hardest part is actually getting used to all method names starting with a capital letter. What I didn’t expect was that it would be possible to developing ASP.NET on a Mac in TextMate, but after a suggestion from a friend to google on “.net without code behind” I found enough to get me started. The server compiles the .aspx and .asmx files on the fly, which is really nice.

The problem

What I wanted was a method that took an XML document and saved it to the right place, and while doing that copying the previous version of that document into a backup directory. I had the first version of the backend up and running in a couple of minutes, but then the problems started.

I did the client side application in Flex (naturally), and when I tried to call the web service from Flex and send the XML document I only got errors. At first I thought the error would be on the server, given that I know just about nothing about .NET. However, after sniffing the network traffic, I would rule that out. The request Flex sent didn’t contain the XML document at all.

On the server side the method looks something like this:

[WebMethod]
public void SaveXmlDoc( XmlNode xmlDoc ) {

When calling this method from Flex with an E4X XML document it gets serialized like this:

<@id>
    root
</@id>

Which isn’t really how it looks when I trace the output of toXMLString

The WSDL describes the type of the parameter as <any/>, and I suspect that Flex doesn’t know how to deal with this. As far I as understand web services Flex ought to have sent the data as inline XML and perhaps that is what it tries to do, but fails when serializing and it ends up as the snipplet above.

At this point you might say that I should have described the type properly and not declare the parameter as <any/>. The problem is that this XML is just generic XML, it has to particular schema, and could even be in different formats. What I want to do, specifically, is to send arbitrary XML. The server side doesn’t have to touch the XML data, just write it to a file.

Solution

I came up with two solutions to the problem: If you don’t care about web services you could just as well create a simple .aspx script and post the XML to that. If you want to use web services, for example if the rest of the server communication uses other web service methods, you can Base64 encode the XML and decode it on the server side. This is quite easy to do in both Flex and .NET.

Grab Steve Webster’s Base64 class and just use the result of Base64.encode(document.toXMLString()) as a parameter to the web service. Edit: seems like there is Base64 utilities in Flex 3 (mx.utils.Base64Decoder and mx.utils.Base64Encoder), so use that if you target Flex 3.

On the server side you can decode the data with this snipplet:

private string DecodeBase64String( string base64EncodedString ) {
    byte[] decodedBytes = Convert.FromBase64String(base64EncodedString);

return new UTF8Encoding().GetString(decodedBytes);

}

Depending on what you want to do you can save the string to a file directly or load it up in a XmlDocument. It works fine and feels like a completely OK solution. It would have been nicer not having to encode and decode, but I don’t mind very much.

Leave a Reply