Re: [Zope-dev] ZPatterns design questions
At 12:50 PM 10/7/00 -0700, Michael Bernstein wrote: "Phillip J. Eby" wrote: Presentation logic lives with an object's class, and deals with what that object knows about presenting itself. UI implementation is "glue" presentation that lives in a Specialist for use by any object that needs to present UI related to objects of the kind the Specialist handles. The terms used here are "official" terminology with precise definitions, btw. I am just trying to answer your questions as best I know how. I'm not sure, but did you mean 'are not' in that last sentence? Whoops. :( Yes, you're correct, I lost the 'not' somewhere along the way there. Here is where my 'Specialist/Generalist' confusion came from. It seems to me, that the simple implementation (you might also call it the default implementation) for the selector UI in your example should be contained in a 'Generalist' object that could be overridden by a 'Specialist'. This would help make crystal clear the line between Presentation Logic and Implementation UI, and would also serve as a useful starting point for creating the overriding methods in the 'Specialist' by the framework customizer. Hm. It seems to me to add too many entities without any real advantages. It's straightforward to have overrideable default implementations in a Specialist - note LoginManager's login, logout, and forbidden pages, which are UI snippets of this sort. Okay, you've got me there. I tend not to think of it that way, if only because there are many things less than satisfactory about its current state of implementation. For example, if we had it to do over again, I would re-work the internal API so that roles, domains, authentication, etc., could be controlled by plug-ins on the user sources. At that point there would be no need for different kinds of user sources, as they would all be fully generic. But anyway, I digress. In light of my own dificulties in adding SMB authentication to PersistentUserSouce.py, and Bill Andersons dificulties with password encryption on some Unices, I think that this would be a *very* worthwhile effort. Such a project might also give you the mandate to get DC to fix the Zope internal acl_users interfaces that were getting in your way. How large of a project would this be? Not very hard, I think. Basically I think we'd warp the "Data Plug-Ins" plug-in group on UserSource to allow what I'll call "authorization plug-ins" to be included. And, we'd complement that with some of the work Ty's already done on mapping roles, domains, etc. back onto plain object attributes so that you can just use regular attribute providers or SkinScript to compute them. I'm not sure, but I think I recall that we even came up with a way to securely manage a password attribute, which we needed for one of our own applications a month or two ago. ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
"Phillip J. Eby" wrote: How (and why) do you distinguish between UI implementation and presentation logic? Presentation logic lives with an object's class, and deals with what that object knows about presenting itself. UI implementation is "glue" presentation that lives in a Specialist for use by any object that needs to present UI related to objects of the kind the Specialist handles. The terms used here are "official" terminology with precise definitions, btw. I am just trying to answer your questions as best I know how. I'm not sure, but did you mean 'are not' in that last sentence? An example of presentation logic would be a method which displays a form to perform some action on the object. E.g., let's say we have a "Task" object with an "Assign To" form. Tasks are assigned to Assignees, but in a given application, there could be many possible kinds of Assignees and the means of selecting an Assignee is context-dependent. Thus, a Task's presentation logic cannot implement such a thing directly; it must ask the Assignees specialist for a code snippet (UI implementation) that displays an assignee selection sub-form within its "Assign To" form. [snip] The Assignees specialist is responsible for providing an appropriate UI implementation (hence the name) for this operation. It could provide a dropdown list, a type-in box with a button to pop up a search window that lets you search the employee directory, or any number of other possible implementations that would get the necessary data back to the assignment method once the form was submitted. We could include a simple implementation with our task management framework, and the application integrator would override it if needed for their situation. Thanks, this is starting to make a lot of sense WRT reusable frameworks. Here is where my 'Specialist/Generalist' confusion came from. It seems to me, that the simple implementation (you might also call it the default implementation) for the selector UI in your example should be contained in a 'Generalist' object that could be overridden by a 'Specialist'. This would help make crystal clear the line between Presentation Logic and Implementation UI, and would also serve as a useful starting point for creating the overriding methods in the 'Specialist' by the framework customizer. We have not yet released any actual frameworks based on ZPatterns, [snip] Isn't LoginManager a framework? Okay, you've got me there. I tend not to think of it that way, if only because there are many things less than satisfactory about its current state of implementation. For example, if we had it to do over again, I would re-work the internal API so that roles, domains, authentication, etc., could be controlled by plug-ins on the user sources. At that point there would be no need for different kinds of user sources, as they would all be fully generic. But anyway, I digress. In light of my own dificulties in adding SMB authentication to PersistentUserSouce.py, and Bill Andersons dificulties with password encryption on some Unices, I think that this would be a *very* worthwhile effort. Such a project might also give you the mandate to get DC to fix the Zope internal acl_users interfaces that were getting in your way. How large of a project would this be? Thanks for your patience in answering my questions. I think I'm getting a good understanding of this approach, but I'm still working on internalizing it. Michael Bernstein. ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
Steve Spicklemire wrote: - How does this product (simple though it is) exemplify the RIPP approach? pje I'm not sure that you can say it *exemplifies* the RIPP pje approach, although it certainly goes along with that pje approach. My hesitation is mainly that it doesn't really pje show any of RIPP's major benefits, which are associated with pje framework re-use and integration. For that, you really need pje to have more than one kind of object, with some kind of pje collaboration taking place. Hmm.. can anyone thing of a good collaboration 'partner' for a simple ToDo list? If it's not too complex.. I'd be happy to add it. I've thought about this since yesterday, and the simplest kind of 'partner' that I can imagine for a 'ToDo', would be a 'Deliverable'. A deliverable would probably have a title, it's own 'Done' boolean property, and probably an optional DeliverableURL property. I'm not sure if it would need it's own 'Doer'. ToDo would need to be reworked so that it's 'Done' property could only be set if all associated Deliverables (if any) were also done (Steve McConnel (sp?) calls these 'binary milestones'). What do you think, is that simple enough? Michael Bernstein. ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
I should point out a couple of things that might not be obvious (that I noticed only on a second 'read' of the explaination): 1) getPersistentItemIds() can be a pain. dtml-in "defaultRack.getPersistentItemIDs()" sort is straightforward enough... but what if I don't care if they are sorted, or I want to sort on some other property? One would think that you could do something like...: dtml-let foo="[]" dtml-in "defaultRack.getPersistentItemIDs()" dtml-call "foo.append(defaultRack.getItem(_['sequence-item']))" /dtml-in dtml-in foo sort=description ... /dtml-in /dtml-let But it doesn't work! You get 'Authorization Failed'. There was a bit of email on the list when I found this problem but it doesn't seem to bother anyone too much it turns out that getPersistentItemIds() actually returns a BTree object, which is not covered by the Zope security system as an allowed 'simple' subobject. However, when you 'sort' the list in the 'in' tag.. a side effect is that it it copied to a plain old Zope list. so it's OK. ;-) So... you *can* do dtml-let foo="[]" dtml-in "defaultRack.getPersistentItemIDs()" sort dtml-call "foo.append(defaultRack.getItem(_['sequence-item']))" /dtml-in dtml-in foo sort=description ... /dtml-in /dtml-let Soo.. the moral of that story is... if you're not allowed to see something... just sort it! :-) !! ;-( 2) This simple/dumb example using a Specialist/Rack combination. There is another approach (that Steve Alexander has used a lot I gather) which is to use the Folder with customizer support. I've never tried that since I went down this road and wanted to sort it out before 'branching' to other methods. To be fair I should probably try to implement this same example with that approach. -steve ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
Ack.. sorry... I was making little changes last night to make sure the ZClass was completely consistent with my explaination, and to make sure I could start 'from scratch'. I created a 'new' ZClass, and a 'new' rack. This confused the 'old' Rack. (I didn't update the ToDoManager.zexp, so if you downloaded the new Product, but the old ToDoManager you got the _setRack error. Anyway... I've now uploaded both the ToDoManager and the ToDoProducts at 0.0.2. I also changed the index_html of the ToDoManager to illustrated the getPersistentItemIds() issue I wrote about earlier good luck! -steve here's the new index_html: dtml-var standard_html_header center br h2dtml-var title/h2 p dtml-let idList="[]" dtml-in "defaultRack.getPersistentItemIDs()" sort dtml-call "idList.append(getItem(_['sequence-item']))" /dtml-in dtml-in idList sort=description dtml-if sequence-start form action="." method="post" table cellspacing=3 cellpadding=3 border=1 trtdnbsp;/tdthName/ththDescription/ththDoer/ththDone?/th/tr /dtml-if tr tdinput type=checkbox name="ids:list" value="dtml-id;"/td tda href="dtml-var id url_quote/editInstanceForm"dtml-var id/a/td tddtml-var descriptionnbsp;/td tddtml-var doernbsp;/td tddtml-if doneDone!dtml-elsenbsp;/dtml-if/td dtml-if sequence-end trtd colspan=5 align=centerinput type=submit name="newToDoForm:method" value="Add New ToDo"input type=submit name="deleteInstances:method" value="Delete selected ToDos"/td/tr /table /dtml-if dtml-else Sorry.. no "to do"s! br form action="." input type=submit name="newToDoForm:method" value="Add New ToDo" /form /dtml-in /p /dtml-let /center dtml-var standard_html_footer ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
Steve Spicklemire wrote: Ack.. sorry... I was making little changes last night to make sure the ZClass was completely consistent with my explaination, and to make sure I could start 'from scratch'. Ok, I just got through stepping through the walkthrough. Thanks! That *was* a really simple example. Perfect! I had a few comments: - You skipped over creating the Product in the Products folder. - Propertysheets: You don't expressly say that Shared needs to be a 'Common Instance Property Sheet'. - ToDoManager: I was initially confused as to where this needed to be created. I tried placing it directly in the Product as well as in the ZCLass before I tried placing it in a normal folder. Ok, moving forward, I had some questions about this approach to building applications: - What do I need to do to let users add ToDoManagers to their own folders without creating them from scratch? In other words, How do I turn ToDoManager into a product? - The term 'Specialist' implies (at least to me) that this object is overiding/replacing a 'Generalist' somewhere, but this does not seem to be the case here. Am I missing something? - I'm trying to reconcile PJE's methodology of Domain Logic, Presentation Logic, Data Management Implementation Logic, and User Interface Implementation Logic. Can you (or Phillip) label each of the DTML methods as to which category they fall into? And state why, even if it seems obvious? - How does this product (simple though it is) exemplify the RIPP approach? In other words, assume I'm asking annoying whiny two-year-old 'why?' questions after every declarative statement in the tutorial. Anyway, I'll try to synthesize all of the replies I get (if any) into a beginners 'Zen of ZPatterns' tutorial. Thanks again for such a simple example! Michael Bernstein. ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
At 07:59 AM 10/5/00 -0700, Michael Bernstein wrote: "Phillip J. Eby" wrote: Domain logic: methods which implement the basic behavior of an object, by manipulating its attributes and by calling methods on itself or other objects. (Including delegation to a Specialist, its own or another.) Presentation logic: "view" methods which implement user interface by displaying object attributes and/or the results of either presentation or domain methods, and "controller/view" methods which call domain logic methods and display results. Implementation logic: All of the code and objects contained in a Specialist which map between the domain model of an object and its physical storage implementation(s). This category can be further subdivided into data management implementation, and UI implementation. DM implementation deals with storing and retrieving objects and associated data, and firing off of implementation rules (e.g. ensure that all objects which meet such-and-such criteria are cataloged in catalog Foo). UI implementation deals with providing snippets suitable for use by collaborating classes and/or specialists. For example, [snip] How (and why) do you distinguish between UI implementation and presentation logic? Presentation logic lives with an object's class, and deals with what that object knows about presenting itself. UI implementation is "glue" presentation that lives in a Specialist for use by any object that needs to present UI related to objects of the kind the Specialist handles. The terms used here are "official" terminology with precise definitions, btw. I am just trying to answer your questions as best I know how. An example of presentation logic would be a method which displays a form to perform some action on the object. E.g., let's say we have a "Task" object with an "Assign To" form. Tasks are assigned to Assignees, but in a given application, there could be many possible kinds of Assignees and the means of selecting an Assignee is context-dependent. Thus, a Task's presentation logic cannot implement such a thing directly; it must ask the Assignees specialist for a code snippet (UI implementation) that displays an assignee selection sub-form within its "Assign To" form. As a counter-example to the above, consider Zope's local roles UI. When you assign local roles, Zope goes to the specialist "acl_users" and asks it for all possible users, then displays them in a dropdown list. While we could do the same thing in our Task/Assignees example (i.e. have Task just display a dropdown list of all Assignees), this is bad because it does not scale well. What if our Task object is used for a company intranet where there are 10,000 employees? What if assignees can be either employees or outside vendors, and they are looked up differently? The Assignees specialist is responsible for providing an appropriate UI implementation (hence the name) for this operation. It could provide a dropdown list, a type-in box with a button to pop up a search window that lets you search the employee directory, or any number of other possible implementations that would get the necessary data back to the assignment method once the form was submitted. We could include a simple implementation with our task management framework, and the application integrator would override it if needed for their situation. This is what UI implementation logic is for, and it's an important part of the rationale for the existence of Specialists (formerly known as Implementors). Our current practice is to place both domain and presentation logic in ZClasses, [snip] Do domain and presentation logic methods go into the *same* ZClass, or separate ones (I realize that this may be a stupid question)? Same one. We assume that it is more useful/important for a framework to offer ready-to-use classes than lots of mixins. dropping down to ExternalMethods or Python bases for the ZClasses when domain logic requires things you can't do in DTML or PythonMethods. Domain and presentation logic are kept to seperate methods, so that domain logic methods can be re-used for XML-RPC or other programmatic interfaces. Presentation is usually done in a flexible way, relying upon UI implementation hooks where sensible. (Since objects under a specialist acquire from the specialist, it's easy to hook to a specialist-level utility method.) I understood what you were saying until the parentheses. Could you repeat that part in a different way? Objects retrieved from a Specialist (in general) have the Specialist as their aq_parent. This means that if an object wants to use UI implementation snippets from its own Specialist, it can do so without having to explicitly name the specialist. This is useful for two kinds of snippets: 1) lookup snippets as described earlier, and 2) configuration snippets, ala standard_html_header, which can be used to customize the look of the presentation logic. We have not yet
Re: [Zope-dev] ZPatterns design questions
At 03:44 PM 10/6/00 -0500, Michael Bernstein wrote: Steve Spicklemire wrote: Ack.. sorry... I was making little changes last night to make sure the ZClass was completely consistent with my explaination, and to make sure I could start 'from scratch'. Ok, I just got through stepping through the walkthrough. Thanks! That *was* a really simple example. Perfect! I had a few comments: - You skipped over creating the Product in the Products folder. Yep, gotta do that. - Propertysheets: You don't expressly say that Shared needs to be a 'Common Instance Property Sheet'. Actually, if it's intended to be shared across all instances, there seems to me to be little reason to have it in the ZClass; you might as well define the properties as constants using SkinScript. However, if you want to have defaults that an application integrator will be able to override without actually subclassing, then you want Shared to be a DataSkin Property Sheet, so that they will have the option of overriding your defaults with SkinScript or another attribute provider. - ToDoManager: I was initially confused as to where this needed to be created. I tried placing it directly in the Product as well as in the ZCLass before I tried placing it in a normal folder. Yes, Specialists go in the application space, as they are part of the application. A product developer may want to create one in the product, but only so that it can be copied into application space by a factory. Btw, in strict RIPP convention, ToDoManager would be named "ToDos", as the plural form of the role the objects play in the framework. Ok, moving forward, I had some questions about this approach to building applications: - What do I need to do to let users add ToDoManagers to their own folders without creating them from scratch? In other words, How do I turn ToDoManager into a product? You can put it in the product, then create two methods - a constructor form and a constructor method, along with a Permission. Last, create a Zope Factory that calls the constructor form. The constructor method would copy the specialist and paste it into the chosen destination. - The term 'Specialist' implies (at least to me) that this object is overiding/replacing a 'Generalist' somewhere, but this does not seem to be the case here. Am I missing something? Specialist means "one who specializes", not "thing which is specialized". :) There are no Generalists, unless you consider the application/Zope site as a whole to be one. :) - I'm trying to reconcile PJE's methodology of Domain Logic, Presentation Logic, Data Management Implementation Logic, and User Interface Implementation Logic. Can you (or Phillip) label each of the DTML methods as to which category they fall into? And state why, even if it seems obvious? In the ZClass: index_html - presentation, because it displays things the object knows editInstanceForm - presentation, because it is strictly display editInstance - primarily domain, but mixes some presentation in. If instead of displaying an OK button, it just did a redirect, I'd consider it a pure domain. Note, by the way, that it's not wrong to mix the two, it's just usually more reusable to keep presentation code out of domain methods if you want to be able to call them from code or XML-RPC and such. In the Specialist (btw, stric: index_html: UI implementation, because it implements a non-object specific UI (i.e. "display all to-do's"). newToDoForm: UI implementation, because it's a non-specific object UI. addNewToDo: DM implementation, polluted by a bit of UI. :) It implements the data management aspect of creating a new instance. It calls the Specialist's newItem() method, but it could have directly called a newItem() method on one of the Specialist's Racks, or done something else to create the instance. deleteInstances: DM implementation, again with a touch of UI. It implements the data management aspect of creating a new instance. Instead of doing manage_delete on each item, this could have been implemented as an SQLMethod that did a DELETE WHERE operation using the id's that were given (if the data store was an SQL database, of course). - How does this product (simple though it is) exemplify the RIPP approach? I'm not sure that you can say it *exemplifies* the RIPP approach, although it certainly goes along with that approach. My hesitation is mainly that it doesn't really show any of RIPP's major benefits, which are associated with framework re-use and integration. For that, you really need to have more than one kind of object, with some kind of collaboration taking place. ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
"pje" == Phillip J Eby [EMAIL PROTECTED] writes: - Propertysheets: You don't expressly say that Shared needs to be a 'Common Instance Property Sheet'. pje Actually, if it's intended to be shared across all instances, pje there seems to me to be little reason to have it in the pje ZClass; you might as well define the properties as constants pje using SkinScript. However, if you want to have defaults that pje an application integrator will be able to override without pje actually subclassing, then you want Shared to be a DataSkin pje Property Sheet, so that they will have the option of pje overriding your defaults with SkinScript or another attribute pje provider. Yeah.. now that I think about it a little more clearly, it makes sense to define this in the Specialist itself. This way all the instances in a ToDoManager would share the same set of 'doers', but different ToDoManagers could keep their own custom set. - I'm trying to reconcile PJE's methodology of Domain Logic, Presentation Logic, Data Management Implementation Logic, and User Interface Implementation Logic. Can you (or Phillip) label each of the DTML methods as to which category they fall into? And state why, even if it seems obvious? pje In the ZClass: pje index_html - presentation, because it displays things the pje object knows pje editInstanceForm - presentation, because it is strictly pje display pje editInstance - primarily domain, but mixes some presentation pje in. If instead of displaying an OK button, it just did a pje redirect, I'd consider it a pure domain. Note, by the way, pje that it's not wrong to mix the two, it's just usually more pje reusable to keep presentation code out of domain methods if pje you want to be able to call them from code or XML-RPC and pje such. Good! This is the kind of feedback I need! So I can pass in a redirection URL so that the domain code can work in different environments easily. pje In the Specialist (btw, stric: pje index_html: UI implementation, because it implements a pje non-object specific UI (i.e. "display all to-do's"). pje newToDoForm: UI implementation, because it's a non-specific pje object UI. pje addNewToDo: DM implementation, polluted by a bit of UI. :) pje It implements the data management aspect of creating a new pje instance. It calls the Specialist's newItem() method, but it pje could have directly called a newItem() method on one of the pje Specialist's Racks, or done something else to create the pje instance. pje deleteInstances: DM implementation, again with a touch of UI. pje It implements the data management aspect of creating a new pje instance. Instead of doing manage_delete on each item, this pje could have been implemented as an SQLMethod that did a DELETE pje WHERE operation using the id's that were given (if the data pje store was an SQL database, of course). OK.. I'll go back and try to 'clean out' the UI pollution to illustrate that separation better. - How does this product (simple though it is) exemplify the RIPP approach? pje I'm not sure that you can say it *exemplifies* the RIPP pje approach, although it certainly goes along with that pje approach. My hesitation is mainly that it doesn't really pje show any of RIPP's major benefits, which are associated with pje framework re-use and integration. For that, you really need pje to have more than one kind of object, with some kind of pje collaboration taking place. Hmm.. can anyone thing of a good collaboration 'partner' for a simple ToDo list? If it's not too complex.. I'd be happy to add it. thanks, -steve P.S. my first alpha of EMarket based on ZPatterns is just about ready. I'm sure it's full of similar pollution. This would be a great place for a design review. ;-) ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
At 09:49 PM 10/4/00 -0700, Michael Bernstein wrote: While I wouldn't say that there has been an actual 'paradigm shift' between the original RIPP presentation and ZPatterns, What's happened is that there's been a lot of "implementation shift". The goals of RIPP have never changed, but they are far from being all available in convenient form in the ZPatterns implementation of that model. That's why ZPatterns' version number is so low - we've implemented less than half of RIPP at this point. Meanwhile, along the way we came up with better ways to do things than we had in our first round of ideas. For example, before we thought of Attribute Providers, we assumed that PropertyHandlers were necessary to implement RIPP designs successfully. And before we thought of SkinScript, we assumed that AttributeProviders would be custom written for different types of databases. And so on. This has caused a lot of shifts in the details of our recommended implementation practices, even though the design philosophy for RIPP applications has not actually changed in the slightest. All that's happened is that implementing such applications is now far easier than Ty or I would have dreamed possible a year ago when we began to formulate the RIPP concepts. (Even though we still haven't got all of RIPP available and occasionally suffer for the lack of some bits like PropertyHandlers.) I'm sufficiently confused at this point to ask for an explanation (with definitions and a *simple* example) of your current thoughts on separating 'domain code' from 'implementation code', both of which still need to be separated from 'presentation code' (DTML interfaces), unless I'm mistaken. Please assume I'm asking a lot of 'why' questions along the way. Domain logic: methods which implement the basic behavior of an object, by manipulating its attributes and by calling methods on itself or other objects. (Including delegation to a Specialist, its own or another.) Presentation logic: "view" methods which implement user interface by displaying object attributes and/or the results of either presentation or domain methods, and "controller/view" methods which call domain logic methods and display results. Implementation logic: All of the code and objects contained in a Specialist which map between the domain model of an object and its physical storage implementation(s). This category can be further subdivided into data management implementation, and UI implementation. DM implementation deals with storing and retrieving objects and associated data, and firing off of implementation rules (e.g. ensure that all objects which meet such-and-such criteria are cataloged in catalog Foo). UI implementation deals with providing snippets suitable for use by collaborating classes and/or specialists. For example, in the DropZone example, the billing sub-application would probably delegate the user interface for presenting a "find customer" form to the Customers specialist, which would contain an appropriate HTML snippet. "Out of the box", that specialist would contain a default find-customer form provided by the creator of the billing framework, and it would be the job of the application integrator to override it to fit the overall application. Our current practice is to place both domain and presentation logic in ZClasses, dropping down to ExternalMethods or Python bases for the ZClasses when domain logic requires things you can't do in DTML or PythonMethods. Domain and presentation logic are kept to seperate methods, so that domain logic methods can be re-used for XML-RPC or other programmatic interfaces. Presentation is usually done in a flexible way, relying upon UI implementation hooks where sensible. (Since objects under a specialist acquire from the specialist, it's easy to hook to a specialist-level utility method.) We have not yet released any actual frameworks based on ZPatterns, but if we were to do so, we would probably also define many UI methods as "class_default_for_X" so that end users could override them with a Class Extender in their Rack or Specialist, without having to subclass our classes. We do not have any "best practice" recommendations in this area as yet, since we haven't had to tackle a project of this nature so far. I'm familiar with the convention of separating 'data' from 'business logic' from 'presentation logic', but this new four-way separation (storage, domain, implementation, UI) is confusing the heck out of me. There's really only three: Presentation, Domain, and Implementation. These largely correspond to Coad's UI, PD, and DM/SI, although we're also mixing UI snippets into the DM/SI part, simply because that's the locale for customization/integration. (In general, we do not assume that placing more than one kind of thing together as neighbors in the same place is a problem. It's what things *reference* that makes their implementation clean or dirty, not necessarily who their neighbors are in the
Re: [Zope-dev] ZPatterns design questions
"Phillip J. Eby" wrote: At 09:49 PM 10/4/00 -0700, Michael Bernstein wrote: While I wouldn't say that there has been an actual 'paradigm shift' between the original RIPP presentation and ZPatterns, What's happened is that there's been a lot of "implementation shift". The goals of RIPP have never changed, but they are far from being all available in convenient form in the ZPatterns implementation of that model. [snip] - we've implemented less than half of RIPP at this point. Ok, That's what's been confusing me. I was thinking that at least some of the missing functionality was due to a change of goals. I'm sufficiently confused at this point to ask for an explanation (with definitions and a *simple* example) of your current thoughts on separating 'domain code' from 'implementation code', both of which still need to be separated from 'presentation code' (DTML interfaces), unless I'm mistaken. Please assume I'm asking a lot of 'why' questions along the way. Domain logic: methods which implement the basic behavior of an object, by manipulating its attributes and by calling methods on itself or other objects. (Including delegation to a Specialist, its own or another.) Presentation logic: "view" methods which implement user interface by displaying object attributes and/or the results of either presentation or domain methods, and "controller/view" methods which call domain logic methods and display results. Implementation logic: All of the code and objects contained in a Specialist which map between the domain model of an object and its physical storage implementation(s). This category can be further subdivided into data management implementation, and UI implementation. DM implementation deals with storing and retrieving objects and associated data, and firing off of implementation rules (e.g. ensure that all objects which meet such-and-such criteria are cataloged in catalog Foo). UI implementation deals with providing snippets suitable for use by collaborating classes and/or specialists. For example, [snip] How (and why) do you distinguish between UI implementation and presentation logic? Our current practice is to place both domain and presentation logic in ZClasses, [snip] Do domain and presentation logic methods go into the *same* ZClass, or separate ones (I realize that this may be a stupid question)? dropping down to ExternalMethods or Python bases for the ZClasses when domain logic requires things you can't do in DTML or PythonMethods. Domain and presentation logic are kept to seperate methods, so that domain logic methods can be re-used for XML-RPC or other programmatic interfaces. Presentation is usually done in a flexible way, relying upon UI implementation hooks where sensible. (Since objects under a specialist acquire from the specialist, it's easy to hook to a specialist-level utility method.) I understood what you were saying until the parentheses. Could you repeat that part in a different way? We have not yet released any actual frameworks based on ZPatterns, [snip] Isn't LoginManager a framework? I'm familiar with the convention of separating 'data' from 'business logic' from 'presentation logic', but this new four-way separation (storage, domain, implementation, UI) is confusing the heck out of me. There's really only three: Presentation, Domain, and Implementation. These largely correspond to Coad's UI, PD, and DM/SI, although we're also mixing UI snippets into the DM/SI part, simply because that's the locale for customization/integration. (In general, we do not assume that placing more than one kind of thing together as neighbors in the same place is a problem. It's what things *reference* that makes their implementation clean or dirty, not necessarily who their neighbors are in the Zope object tree.) Ok. That makes some more sense. (still working on the Zen, though) I know that both of you (Phillip and Ty) are very busy right now, but could you perhaps give us a few short installments? Starting at the beginning (wherever that is), of course. How's the above for a beginning? Great! Now I need a really stupid-simple example. Something that could have been implemented trivially by using Zope's built in objects, maybe a ZClass, and a bit of DTML, like a list of press releases, or a FAQ, or a company directory. Something *really* simple, so I can see how it's done with ZPatterns. Thanks, Michael Bernstein. ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
OK.. here's the dumbest example I could cook up. It was my first experiment with ZPatterns in July of last summer. It was based on a really early release, I don't remember which, but it seems to work with the latest.. (I just barely testted it... ) Load the Product ToDoProducts.zexp into the products folder first, then the ToDoManager into a folder in Zope. http://www.zope.org/Members/sspickle/DumbZPatternsExample -steve ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
Ack.. of course I forgot to test creating new instances there was a snippet of code for editing and creating that didn't work with the new propertysheet stuff. I fixed it just now... so it really works. ;-) -steve "Steve" == Steve Spicklemire [EMAIL PROTECTED] writes: Steve OK.. here's the dumbest example I could cook up. It was my Steve first experiment with ZPatterns in July of last summer. It Steve was based on a really early release, I don't remember Steve which, but it seems to work with the latest.. (I just Steve barely testted it... ) Load the Product ToDoProducts.zexp Steve into the products folder first, then the ToDoManager into a Steve folder in Zope. Steve http://www.zope.org/Members/sspickle/DumbZPatternsExample Steve -steve Steve ___ Zope-Dev Steve maillist - [EMAIL PROTECTED] Steve http://lists.zope.org/mailman/listinfo/zope-dev ** No cross Steve posts or HTML encoding! ** (Related lists - Steve http://lists.zope.org/mailman/listinfo/zope-announce Steve http://lists.zope.org/mailman/listinfo/zope ) ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
Steve Spicklemire wrote: Ack.. of course I forgot to test creating new instances there was a snippet of code for editing and creating that didn't work with the new propertysheet stuff. I fixed it just now... so it really works. ;-) I didn't get a chance to play with this today, but I'll make time to do so tomorow. How easy would it be for you to write a step-by-step HowTo/WalkThrough of creating the example? I can edit it and flesh it out if you can write a bare-bones version. Thanks, Michael Bernstein. ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
Again.. this is an embarrassingly trivial example.. but here it goes: First of all there is a ZClass 'ToDoClass'. It needs to have a base class of ZPatterns:DataSkin. You don't need constructor methods, but I don't think they hurt anything if you leave them in. The ToDo needs methods: index_html to render itself like any ZClass: -- dtml-var standard_html_header center table trthName/thtddtml-id;/td/tr trthDescription/thtddtml-description;/td/tr trthDoer/thtddtml-doer;nbsp;/td/tr trthDone?/thtddtml-if doneDone!/dtml-ifdtml-done;nbsp;/td/tr trthLast Modified/thtddtml-bobobase_modification_time;/td/tr /table a href="editInstanceForm"Edit this instance/a a href="dtml-URL2;"Back to list/a center dtml-var standard_html_footer -- editInstanceForm so folks can edit its contents... (just like any ZClass) -- dtml-var standard_html_header center h2Edit ToDo Item/h2 form action="editInstance" method="post" table cellspacing=3 cellpadding=3 trthName/thtddtml-id;/td/tr trthDescription/thtdtextarea name="description" wrap=soft cols=60 rows=15dtml-description;/textarea/td/tr trthDoer/thtdselect name="doer"option value=""Nobody dtml-in doers sort option value="dtml-sequence-item;" dtml-if "doer==_['sequence-item']"selected/dtml-ifdtml-sequence-item; /dtml-in /select /td/tr trthDone?/thtdinput type=checkbox name="done" dtml-if donechecked/dtml-if/td/tr trtd colspan=2 align=centerinput type=submit value="Edit ToDo"/td/tr /table /form /center dtml-var standard_html_footer -- a method that actually does the changing of the properties... (just like...) editInstance -- dtml-var standard_html_header center dtml-if "REQUEST.form.has_key('done')" !-- booleans can be tricky.. -- dtml-call "REQUEST.set('done',1)" dtml-else dtml-call "REQUEST.set('done',0)" /dtml-if dtml-call "propertysheets.Basic.manage_changeProperties(REQUEST=REQUEST)" ToDo Changed.br form action="dtml-URL2;" input type=submit value="OK" /form /center dtml-var standard_html_footer -- That's it for the methods of the ZClass...we can view/edit instances TTW. Now.. we need propertysheets: Basic: (Now it's a "Data Skin Attribute Property Sheet"). properties: description (text) doer (string) done (boolean) Shared: (This is a propertysheet that's meant to be shared by all the instances. If you update this... update it in the ZClass, not an instance.) doers (lines) Finally... we need methods for the ToDoManager (Specialist): We'll set the defaultRack of the ToDoManager up to store its objects persistently, using the ToDoClass we just created as the storage type. We can just leave the default data plugins installed since they work fine with persistent storage. If later you want to experiment with other storage methods, you can do it making almost no changes to any other code (with the possible exception of defaultRack.getPersistentItemIds() which might not be appropriate if you're not using persistent ZODB storage) Here is the default method of the ToDoManager... basically, pull out the objects and view a brief list of ids, descriptions doers, and doneness... : -- dtml-var standard_html_header center br h2dtml-var title/h2 p dtml-in "defaultRack.getPersistentItemIDs()" sort dtml-if sequence-start form action="." method="post" table cellspacing=3 cellpadding=3 border=1 trtdnbsp;/tdthName/ththDescription/ththDoer/ththDone?/th/tr /dtml-if dtml-let currID="_['sequence-item']" dtml-with "getItem(currID)" tr tdinput type=checkbox name="ids:list" value="dtml-currID;"/td tda href="dtml-var currID url_quote/editInstanceForm"dtml-var currID/a/td tddtml-var descriptionnbsp;/td tddtml-var doernbsp;/td tddtml-if doneDone!dtml-elsenbsp;/dtml-if/td /dtml-with /dtml-let dtml-if sequence-end trtd colspan=5 align=centerinput type=submit name="newToDoForm:method" value="Add New ToDo"input type=submit name="deleteInstances:method" value="Delete selected ToDos"/td/tr /table /dtml-if dtml-else Sorry.. no "to do"s! br form action="." input type=submit name="newToDoForm:method" value="Add New ToDo" /form /dtml-in /p /center dtml-var standard_html_footer -- We also need to be able to add and delete items from the rack: newToDoForm: -- dtml-var standard_html_header center form action="addNewToDo" method="post" table trtd align=center colspan=2h2Add New ToDo/h2/td/tr trthToDo Name/thtdinput name="name" size=40/td/tr trthToDo
Re: [Zope-dev] ZPatterns design questions
Steve Spicklemire wrote: Again.. this is an embarrassingly trivial example.. but here it goes: [snip details] That's it. I can't imagine anything simpler. ;-) Really! Thanks, I'll be trying this out at work tomorrow. Michael Bernstein. ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )
Re: [Zope-dev] ZPatterns design questions
Phillip J. Eby wrote: If I can offer a suggestion... Please... It sounds to me like you don't need SheetProviders at all, if you effectively define the property sheets as part of your class, and make the attributes direct attributes on the DataSkin. You then need only set Ok, I'm feeling pretty stupid right now but I have to ask what you mean by "define the property sheets as part of your class"? Do you mean using something like this in the DataSkin subclass: def __init__(self,id): self.DataSkin.__init__(self,id) ps = self.propertysheets ps.manage_addPropertySheet('CompanyData','CompanyData') ps.get('CompanyData')._properties = ( {'id':'name', 'type':'string', 'mode':'w'}, ... ) up a single trigger that checks whether any of the attributes you want to mirror have changed, and then fires that off to the SQL db. It would By 'trigger' you are referring to a RuleAgent plugin? Hmm... I had briefly thought about this, but most of the discussions relating to interfacing to an external RDB seemed to indicate subclassing a SheetProvider was the best course of action. I'll have look into this (hadn't spent much time figuring out RuleAgents yet). actually be a bit easier to set up if you were using a ZClass, since you could create the property sheets there by just adding "DataSkin Property Sheet" objects to the ZClass. But the basic principle would still apply. We've come to the conclusion that ZClasses really are more a hinderance than a help, trading functionality for shorter learning curve. With straight python code you get much more control and the ability to use conventional editors and tools (cvs), without losing anything besides a bit of time figuring things out (which is better in the long run anyways). -- John Eikenberry [[EMAIL PROTECTED] - http://zhar.net] __ "A society that will trade a little liberty for a little order will deserve neither and lose both." --B. Franklin ___ Zope-Dev maillist - [EMAIL PROTECTED] http://lists.zope.org/mailman/listinfo/zope-dev ** No cross posts or HTML encoding! ** (Related lists - http://lists.zope.org/mailman/listinfo/zope-announce http://lists.zope.org/mailman/listinfo/zope )