ZPatterns, ObjectDomain, UML and all that.....
I've been working out some issues with EMarket, and as a way to 'clear the cruft'.. I decided to bite the bullet and do some more careful object modeling. Other than scribbling on paper, and making up some diagrams that look a little like those from Coad's book on Patterns and Strategies, I've never used any object modeling tools before in my life. Soooo... I downloaded the eval version of ObjectDomain, and I can go for about 5 minutes on a Mac before it crashes, and usually 10 or 15 on Windows before it stops responding to mouse/keyboard input. Save early, save often.. ;->. Sure it's frustrating.... but it seems more workable that ArgoUML which I've had even less luck with.... (What are other folks using? Rose?) anyway after much more time that I would have thought possible I've come up with: http://www.zope.org/Members/sspickle/EMarket/objectModel.gif which is not finished, correct, or even totally consistent with the current implementation, but it's a starting point. Based on this picture.... I have some questions for other folks out there who are doing object modeling and using ZPatterns, or who might just be willing to comment on a first hack at a model for EMarket. ---------------------------------------------------------------------- 1) One of my areas of confusion relates to the notion of an 'association'/'aggregation'. It seems that you can have a 'simple association', which I guess just means that one object can talk to another as equal 'peers'? This is denoted with a simple line, with no bubbles at either end. There is also 'composite aggregation', with a filled in bubble at one end (the container/master) and nothing at the other (contained/slave?). Finally there is 'shared aggregation', where there are multiple 'masters/containers' for a single 'slave/contained' object. Each 'master' in this case has an 'empty' bubble. Object domain has three labels for each connection. 1) a name for the connection itself, 2) a name for the source/from end, and 3) a name for the sink/to end. In the current implementation of EMarket, since the connections are actually implemented as Specialists, the only real connections is that a master/container will have a (possibly) empty list of ids that can be used to fetch the actual slave/contained object from the corresponding Specialist(s). In the case of a 'two way connection' would the connection have the name of one specialist in one direction, and another in the other direction: e.g., Shopper <--baskets ---- shoppers---> Basket)? Does this make sense? Are there other/better ways to think about and/or implement this idea with ZPatterns? ---------------------------------------------------------------------- 2) I've stumbled on different ways to implement these things. I'm sure there are other (better?) ways as well. One way e.g., is to store a 'barID' to make a connection, and a runtime, using "bars.getItem(self.barID )" to get it.. or.. store the Bar object itself in your DataSkin and hope that everything will sort it self out when it is next accessed. So far I've always kept an ID, then used getItem at runtime, when I needed the 'real' thing.... I remember some discussion on the list about keeping an Address object in a related DataSkin, which sounds great.. but I have/had some concerns. My retrieval code often looks something like this: theBar = bars.getItem(self.theBarID) if theBar: foo = theBar.getFoo() else: # do something about the fact that there was no Bar..... If I explicitly store a Bar object as an Attribute of a DataSkin then what happens if the original Bar is removed from its Specialist's Rack? Does the Bar I store still refer to the original Rack as its DataManager? So.. does a Rack sometimes have 'clients' that are not really in the Rack at all? Or perhaps I misunderstood the discussion, and the Address wasn't really a DataSkin at all? Also.. assuming that all works, do I have to do anything special, or carefully to be sure that the persistence machinery doesn't incur lots of expensive attribute fetching if I don't explicitly refer to those attributes, but have the DataSkin as a directly set attribute of another DataSkin? Another approach is to make theBar a computer attribute, e.g., WITH bars.getItem(self.theBarID) COMPUTE theBar=RESULT or NOT_FOUND which is sort of a (nice?) compromise between the two approaches, but it still requires that I keep an Id around.... Does anyone have comments/feedback on the merits of these different approaches? I'd love to come up with a set of 'best practices' for some of these issues. I'm trying to use ZPatterns, train other folks on how to use them, and learn the nitty gritties all at the same time... Life never used to be so interesting. ;-> ---------------------------------------------------------------------- 3) (Last question I promise!.. for now) Is there any real difference between the plain lines, open bubbles, and closed bubbles other than the number of (master) objects with relations to the (slave?). If both objects refer back to eachother, should there be two bubbles? (That doesn't seem to be an option with ObjectDomain.) Is there a good source on the net that talks about this stuff? I've been reading some of the specs at omg.org... and I'm guessing there's something out there more friendly ... but I haven't found it yet... ---------------------------------------------------------------------- OK.. that's it. Any feedback would be appreciated. When I get it all figured out I'll throw it all into the DumbZPatterns example with your feedback. thanks! -steve
Steve Spicklemire wrote:
3) (Last question I promise!.. for now) Is there any real difference between the plain lines, open bubbles, and closed bubbles other than the number of (master) objects with relations to the (slave?). If both objects refer back to eachother, should there be two bubbles? (That doesn't seem to be an option with ObjectDomain.) Is there a good source on the net that talks about this stuff? I've been reading some of the specs at omg.org... and I'm guessing there's something out there more friendly ... but I haven't found it yet...
First off, a disclaimer: I don't think UML is all that helpful fr modeling Zope applications, or ZPatterns applications. I'll explain why some other time. The "bubbles2" you're talking about are to indicate aggregation and composition. These are different from the cardinality of the relationship. See http://www.cat-box.net/steve/umltalk/page11.html for an example of a plain association, an association that says "a person may keep any number of cats, but a cat only has one owner", and an association with the roles "pet" and "owner". On http://www.cat-box.net/steve/umltalk/page13.html, the diagram shows aggregation and composition. The examples are of a car, and a tooth. The enamel and fillings in a tooth are tightly bound together, and not really separable without pain (!). However, you can remove the engine and wheels from a car, and consider them separately, without too much trouble. So, the car example is aggregation, the tooth example is composition. In UML, objects linked by composition are semantically equivalent to attributes. So, in the tooth example, I could have had the enamel and collection of fillings as attributes of the tooth. Aggregation indicates a responsibility in the relationship. So, in the Car example, if I sell my car, or scrap my car, the engine and wheels go as well. However, if I break my car's engine, that has no implications for the rest of the car or its wheels, except that I need a new engine. When you're expressing object-oriented designs, an aggregate relationship implies that the controlling object (the "master", with the diamond next to it) is responsible for creating, destroying, and answering queries about its aggregate objects. If you want to learn UML, I recommend "Practical Object-Oriented Design with UML", Mark Priestley, pub. McGraw Hill, ISBN 0-07-079599-5. I think Coad's notation is better and clearer, as it allows you to communicate information about objects and their classes all in one place. Coad's notation is more about showing interactions of objects, whereas UML makes that awkward, and is mostly used for expressing static information about relationships between classes. -- Steve Alexander Software Engineer Cat-Box limited http://www.cat-box.net
participants (2)
-
Steve Alexander -
Steve Spicklemire