PureMVC Architects Lounge

Announcements and General Discussion => Architecture => Topic started by: facorreia on July 30, 2008, 05:56:13

Title: The role of value objects
Post by: facorreia on July 30, 2008, 05:56:13
I am really liking PureMVC a lot. It is clean, well thought-out and very flexible.

As I learn it, I still have some doubts about the role of Value Objects in its architecture. For instance, there is a post (http://forums.puremvc.org/index.php?topic=243.0 (http://forums.puremvc.org/index.php?topic=243.0)) where Cliff says:

Value Objects should be just that, carriers for data. Proxies should generally have the methods that massage that data, translate it or simply expose it to the app.

The main reason for only having attributes on a value object is that it is intended for shuttling data across tiers of an application.

That includes across client and server tiers. When marshaling and unmarshaling an object into a transfer format like XML, you can only send values. The methods wont go, or necessarily even make sense on the other side.

OK... First of all, in the Employees example, the UserVO is not a pure Value Object in this sense. It has two methods: isValid() and givenName(). So it is more like a Domain Object, which seems to be benefic to the application.

Next, the quote describes a Value Object as a Data Transfer Object that should only contain data, not any behavior, and that will be shuttled between application layers, including between client and server.

Now, it seems I can easily use an anonymous object as a DTO between the client and the server. It also seems that the client application should not be too tied to the way the server represents the data. I would consider the DTO as a kind of calling protocol to the service, that could possibly require conversion to data types more adequate for a client application. Again, it seems odd that a view component would receive the same DTO that would be returned by a remote service.

Let me try to clarify my thoughts with an example.

A "Project" entity could have a "Manager" attribute. That could be represented by an integer key on the service. But on the client I would like it to be an instance of a Manager class, not just an integer. Or at least to have also the manager name, that I would retrieve from another proxy, so it would be easier to sort on grids by the manager's name.

I also could want my project objects to have a collection of milestones. In the service that would be represented by another DTO for the Milestone entity, that would probably have the integer ID of the project and a milestone name and due date. But I would like my client-side project object to have a collection of milestones.

I also could want to go full domain object on this, and have the client-side behavior associated to the project on the project object itself, like the sample does with the User object.

I've read the best practices document three times, read all the other documents I could find on this site, downloaded and browsed the examples, created my own sample application (http://fernandoacorreia.wordpress.com/2008/07/30/flex-client-using-puremvc/ (http://fernandoacorreia.wordpress.com/2008/07/30/flex-client-using-puremvc/)), read all articles I could find in blogs about PureMVC, but it is still not very clear to me how we can deal in PureMVC with a database-based scenario like I described (Managers <-> Projects <-> Milestones) and how we can have a client-side abstraction of this objects that is not too restricted by the service interface.

Actually I am not certain if this strategy of using a VO and putting the instance behavior on the proxy is a definite best practice on PureMVC or if it is just a convenience. That is, would I run into trouble if I decided to use anonymous objects as DTOs to the server, use domain objects with attributes and instance methods within the client and kept in the proxy only the methods common in the Repository pattern, like CRUD methods?

The only possible complication I can think of is that the view components would be able to call the methods on the domain objects and that could break the isolation. Then again, that's exactly what the Employees example does with the isValid() and givenName() methods of the User "Domain" object...  :o

Any help will be appreciated.

Title: Re: The role of value objects
Post by: andrew on July 30, 2008, 06:50:53
What is the server technology you are using?  If there is some remoting technology available for that platform like BlazeDS then you can maintain one set of DTOs or VOs or whatever on the server, and then use some tool to generate the AS3 version of this code.  These DTOs are simple "bags or getters and setters" and are totally anemic and don't have behavior. 

If you want, you can wrap these with more functional objects on the client (decorator pattern), or you can use the proxy construct for that.  But the DTO concept is pretty powerful in Flex especially when working with a Java backend because you can tightly couple the client and the server.  Now on the server, these DTOs are probably in a different layer than your "real" domain objects.  They exist for communication to the client, or with other web services.

We send back full DTO object graphs where things like Account contains Users which contain Roles, etc.  And it works out well.

Title: Re: The role of value objects
Post by: facorreia on July 31, 2008, 08:07:41
Andrew, I will use Python with PyAMF. I can happily use anonymous Object instances as DTOs. Or I could create DTO classes to use on the service requests. My post actually is asking if it is a good idea to tie the client-side view to a data structure that makes sense to the server but may not be the best one on the client.

And also I am confused by the talk about VOs being the preferred choice on PureMVC, but the example uses a Domain Object. Although it is named as a UserVO, it is not really a VO.

Title: Re: The role of value objects
Post by: philipSe on July 31, 2008, 09:45:50
As regards maintaining client state, I don't use VOs.  In fact, I don't use VOs at all, but maybe they will arise in the context of client/server transfers sometime in the future.

Data from the server is built into an object graph on the client, e.g. per the example mentioned above, project references manager and project has a collection of milestone objects.  A set of proxies manages the object graph, i.e. the domain model. Mediators and Commands access the domain model via the proxies.  Roughly speaking, there is a proxy class for each record type in the object graph.

In the classic puremvc manner, the proxy contains a collection of records of the particular type.  For each record type, there is also a class, and this class includes appropriate behaviour, to support certain record-level operations best encapsulated there.  This model class includes the record properties - I know that these could be held in a separate VO class and referenced from the model class, but for now they're not.  Record properties can be bindable, to support usage in  view components.