7
votes

Background

Okay I'm one of those guys who NEVER asks questions and who can usually find what I need from existing questions or forums....but alas I have spent the last few days trying to figure this one out and have come up with very little existing information.

I am using Flash Builder 4.6 for PHP Premium to build a Flex application that uses the PHP Zend Frameworks's AMF capabilities to map classes from PHP to Flex and to use them as objects to send back and forth instead of using XML or JSON. Right now I am doing it all on a single local machine for ease.

Issue

I am not having trouble mapping my own custom PHP classes into ActionScript/Flex classes but I cannot for the life of me manage to map a DateTime PHP class into an ActionScript Date class. I have read elsewhere that it automatically maps DateTime objects to Date objects but I have never gotten it to work.

Strangely though, I can get it to work if I replace all instances of, in my case, valueObjects.DateTime (the auto-generated ActionScript class) to Date in the _Super_Foo.as class that has the DateTime property. This basically forces Flex to interpret the data of that property as a Date. However, since all the _Super_XXX.as files are files that autogenerated by Flex, it gets rewritten any time I refresh or edit ANY PHP service that Flex is linking to in Flash Builder.

Remarks

I could of course do this the quick and dirty way by keeping the variable as a string (it's coming from MySQL in a DateTime field) and then just create some functions to convert it to a Date object on the client side but I need a more permanent and stable solution.

Example:

<?php
class Foo {  
  public $id; // int
  public $name; // string
  public $date; // DateTime
  public $bar; // custom object
}
?>

should go to --->

package {
  class Foo {
    public var id:int;
    public var name:String;
    public var date:Date; // native class
    public var bar:Bar;
  }
}

but I am getting

package {
  class Foo {
    public var id:int;
    public var name:String;
    public var date:DateTime; // custom class
    public var bar:Bar;
  }
}

I have tried things such as the following:

  • in the gateway.php file

    $server->setClassMap("Date", "DateTime");
    
  • using the Zend_Date object instead

    $foo->date = new Zend_Date($blah);        
    
  • and after trying to map it as well explicitly

    $server->setClassMap("Date", "Zend_Date");
    
  • the change I currently have working in the _Super_Foo.as file (which gets written over frequently)

    private var _internal_date : valueObjects.DateTime; // custom object
    

    to

    private var _internal_date : Date; // native object
    

    I just need it to do this automatically like I have read it should.

3
i always used a timestamp when passing dates to/from the server. then you can just say: new Date(timestamp).Philipp Kyeck
Ugh. Okay I decided to convert all 50 datetime fields i was using in MySQL to timestamp fields (initially thinking it would be a unix timestamp, which it's not, but it requires 4 bytes instead of 8). Then i changed each property of my object from a DateTime to an int (which was automatically reflected in the AS class) and using strtotime($timestamp) on it . Then I just needed to format the values in Flex by multiplying by 1000 (to milliseconds) and mid-level satisfaction is complete.walkingbrad
You can convert it at PHP level and keep datetime in SQL, I don't understand why you changed your DB. And yes, timestamp (miliseconds) in AS3 is the most reliable way to use dates AFAIK.a.s.t.r.o
Well i changed it, like I said, initially thinking SQL timestamp means a simple integer value. But I kept it because it's more timezone agnostic. However, I am still having issues mapping PHP objects to standard/default Flex objects. Ex: DateTime -> Date, Zend_Amf_Value_ByteArray -> ByteArray It continues to map everything to a custom valueObject on the Flex side when I've seen it working elsewhere as automatically mapped to the standard AS class.walkingbrad
I added a bounty to this question in case you still needed a solution since I see it was unresolved.drew010

3 Answers

0
votes

Well I have to admit, that I usually use BlazeDS on Java and not Zend, but I have had similar problems in transfering Calendar objects (I wanted to prevent loosing the timezone data). For This BlazeDS supported so-called PropertyProxys, which are components that allow to takeover the serialization/deserialization process for certain types.

I would assume that ZEND would support a similar thing. So another option would actually be to make Zend zupport the full Flex type. I have searched a little and it seems that the entire terminology is different in Zend, but I think this stackoverflow article should explain it a little: Zend AMF custom dispatcher

Chris

0
votes

In my experience, Zend Framework has taught me that it offers many features but many times they don't work exactly how you'd expect. For example:

Recently I was working with a bug in "digitalus-cms" (A blog-like framework built on top of ZF) that it couldn't post new articles with a hyphen in their title name. I tracked it down to Zend_Form_Element::filterName. It uses a regular expression that matches any character that falls into the category of: [^a-zA-Z0-9_\x7f-\xff] then removes it. This ends up removing hyphens from the names of form elements which wound up being the cause of the bug.

If Zend_Amf or Zend_Date doesn't work the way you want it to, find a workaround such as passing a unix timestamp number around so everything works the way it should. Then afterwards, you can write a class to extend off one of Zend's classes. Zend Framework is meant to be extended upon, that's the way the framework was built so you can fix issues like these on your own to get the framework to behave how you want it to. That's the whole point of wrappers. Go ahead, create some of your own wrapper classes and toss in some methods to interact with ZF so you can fine-tune everything.

As far as finding the cause of your issue, all I can tell you is keep on debugging and isolating code so you know what you are passing flex, and how flex responses to that. After you play around with it enough, I'm sure you'll find the culprit.