Flex can't do REST

Thijs van der Vossen, 08 Jun 2007, 13:04 in ruby on rails and broken (edit).

If you’re thinking of building a cool snazzy Rich Internet Application front-end in Flex for your RESTful Rails application then please stop dreaming.

There’s no way to extract the headers from an HTTP response in ActionScript 3 so you can’t get the id of a newly created resource from the ‘Location’ header and you can’t tell the difference between a ‘500 Internal Server Error’, a ‘404 Not Found’ or a ‘422 Validation Error’.

There’s also no way to get the response body for anything not in the 2xx range.

Oh, and you can only do a GET or a POST, no PUT or DELETE, at least not without a proxy.

If you can prove me wrong, please do.

Comments

  1. ben about 5 hours later: (delete)

    check out flexible rails on rubyforge...

    "Flexible Rails approach is to scaffold REST controllers and generate Flex (swf) views from models including validations"

    looks like it adds a '_method' parameter to the object that's sent to the http service.

    params['_method'] = "PUT";
    //add other parameters
    resourcePut.url = "/contacts/" + contact_grid.selectedItem.id + ".xml";
    resourcePut.send(params);

  2. Norbert Crombach about 7 hours later: (delete)

    The _method parameter is a Rails trick that allows you to send PUT and DELETE from browsers, which don't support those methods either. While it is usable, it shouldn't have to be done that way. And the lack of proper header support is still a big issue for which there exists no quick workaround.

  3. Thijs van der Vossen about 8 hours later: (delete)

    Even though the _method hack is kinda ugly it's not really a problem.

    The fact that you can't get the headers and the fact that you can't get the body of a non-2xx response makes it impossible to use Flex with proper RESTful Rails applications.

  4. Harris Reynolds about 10 hours later: (delete)

    Here is a money quote from the article you linked to;

    "With the glaring exception of support for response headers, AS3's support for HTTP is full-featured enough to implement just about any REST-style protocol or API. Let's hope the Flex and Apollo teams can fill this one remaining hole in a future release."

    It makes you look dumb to title your article "Flex can't do REST" and then link to an article that says that. Nice to see Rails guys not afraid to pull some FUD tricks.

  5. Harris Reynolds about 10 hours later: (delete)

    Hey there... it's me again. The more I look in to this the more ignorant you look. One thing is for sure... you have done absoutely zero Flex programming yourself.

    Here is a link you may want to check some facts against:

    http://livedocs.adobe.com/flex/2/langref/mx/rpc/http/HTTPService.html

    ... And here is a money quote for you (see doc for the method property): "HTTP method for sending the request. Permitted values are GET, POST, HEAD, OPTIONS, PUT, TRACE and DELETE. Lowercase letters are converted to uppercase letters. The default value is GET."

    You are also wrong about not being able to extract response headers. You can not get access to the headers for HTTP fault codes (404, 500 etc), but you can get access to the headers from the PUT example you use above.

    I guess since you've been proven about 80% wrong maybe its time for an update. No hard feelings of course.

  6. Thijs van der Vossen about 22 hours later: (delete)

    Harris Reynolds, I disagree with Brian Riggs' conclusion that 'AS3's support for HTTP is full-featured enough to implement just about any REST-style protocol or API'.

    So, if you need to hack around the limitations in your Rails application you're not doing REST, you're just misusing HTTP to implement your own RPC interface.

    Even though the Flex documentation says that GET, POST, HEAD, OPTIONS, PUT, TRACE and DELETE are all 'permitted values', everything but GET and POST only works when you're running Flex Data Services 2 as a server-side http proxy.

    I don't agree that you've proven me 'about 80% wrong'. If you want to do that you really have to show me code that works with and ActiveRecord REST interface without needing any changes to the Rails application.

  7. Nathan de Vries 3 days later: (delete | show email)

    @Thijs: You're correct, but there's a couple of details that need to be clarified/corrected:

    http://www.atnan.com/2007/6/11/can-as3-do-rest-or-not

    I hope you don't mind me linking to my website.

  8. Thijs van der Vossen 3 days later: (delete)

    Nathan, thanks for sharing your experiences. I'm going to comment over there.

  9. Alex MacCaw 3 days later: (delete | show email)

    This has always been a problem in Flex. Adobe solved this problem in the Apollo alpha, and gave you access to all the url response codes, extra methods to get response data etc and extra http verbs (PUT/DELETE etc). However, this still doesn't help those people using Flex without Apollo and, until a new Flash release, we'll just have to find ways of working around it. One such way is to build your own http client using the flash socket connection (which has no such limitations). You'll only be limited to domains you can connect to (the old crossdomain.xml issue - not too much of a problem if you have control server side). Rails let's you do every request via a post and add a hacky parameter of _method=put. This lets you do the whole range of http verbs in Flex, but you still don't get the proper http response codes or bodies, and it won't work a backend other than Rails. So, a socket urlloader is the way forward - if you look in the source of my project, ActiveResource for Actionscript you'll find an example of such a class. One bit of further advice - make sure POST requests in Flex have a body, if you don't - they automatically get made to GET ones.
    http://code.google.com/p/as3-active-resource/
    http://as3-active-resource.googlecode.com/svn/trunk/

  10. eonnen 70 days later: (delete)

    Rails isn't quite RESTful out of the box either. Controllers generated by scaffold_resource don't recover from ActiveRecord.find misses at all resulting in a 500 returned to the client when it should really be returning a 404. This true for four of the pre-generated methods so you don't necessarily have the moral high-ground here that Rails is perfect and Flex fallible. Bottom line is that the FVM punts up to the browser for connectivity (unless you write a raw socket impl) and that browsers are not good REST citizens. The overloaded POST hack supported by Rails exists purely because the browser doesn't really do REST well.

  11. Jarrod 181 days later: (delete)

    @Eonnen

    Rails scaffolding was never meant to be an "out of the box" solution for anything other than quickly mapping a database table to a quick and dirty UI. Any professional rails developer is going to end up re-rewriting 75% of the scaffold code (if he/she even used scaffolding in the first place). So yes... rails is RESTful out of the box.

    I also disagree with you that a 404 is the correct response to ActiveRecord::RecordNotFound. 404 implies that the resource itself was not found... not that an item within a resource was not found. The error RecordNotFound is also something that needs to be handled by a rescue which should tell you right there that it is indeed an actual error. If you are passing along garbage ID's to a given resource I definitely think 500 is the proper response instead of a 404 not found which implies that you are not even talking to the correct resource.

    Let's say that the given resource we are talking about is:

    /people

    Let's also say that only ID's 1 through 10 exist within /people. A GET request to:

    /people/11

    should result in a 500 error... /people is an actual resource, but ID 11 is unknown within that resource.

    However...

    /peeeolpe/11

    Should definitely result in a 404 since /peeolpe is an unknown resource.

  12. Manfred Stienstra 181 days later: (delete)

    Not that it's relevant to the original post, but a 404 is absolutely the correct response for when something was Not Found (by definition). In Rails (and most REST implementation) /people/1 is the URL meaning either the first person known or the person with ID 1. When you can't find that person, a 404 is exactly the right response.

  13. Gabe 217 days later: (delete)

    I am working on an as3 http/https client @ http://code.google.com/p/as3httpclientlib/

    With a Socket class you can implement any protocol (including TLS). Currently you can't detect stream output progress, but hopefully they will fix it soon.

  14. sal figeroa 241 days later: (delete)

    I definitely agree with Manfred. Jarrod, 5xx for peeple/11 implies there was an error servicing the request on the server side, not that a person with 11 was not found. 404 is without question the right response.

  15. kenny 280 days later: (delete)

    there is another http library for flex hosted on sourceforge. seems it can do rest too:

    http://sourceforge.net/projects/flexurlloader

  16. Noah 487 days later: (delete)

    Another hack around this - make ExternalInterface calls to a javascript method that uses the browser to send and receive all HTTP methods, request/response headers, etc.

    See http://blog.vihinen.net/2008/10/flash-http-client-limitations.html

  17. josh chan 699 days later: (delete)

    Check this method out using as3httpclientlib:
    http://www.adobe.com/cfusion/communityengine/index.cfm?event=showdetails&;productId=2&postId=14106

  18. M.Elkharashy 839 days later: (delete)

    I have published my recent Actionscript library rest-ar. It can do all rest actions in an easy way. check it

    http://code.google.com/p/rest-arm/

  19. Taylor 881 days later: (delete)

    You should also check out this library, "RESTHttpService" by Dustin Calloway: http://code.google.com/p/resthttpservice/

    It uses sockets to implement the HTTP methods and returns meaningful success and error codes. Since it is designed to be similar to the original HTTPService, its use will seem familiar to most Flex developers.

    By adding a method or two, I have developed a slightly-modified version of RESTHttpService that has allowed me to (easily) write a Mate Invoker class so the service can be used in the same way as the "native" Mate service invokers.

Add your comment

In order to fight spam on this blog, posting comments from a browser without javascript is currently not supported.