Overriding __getattr__ for requests only.
Hello, everyone. I am trying to write a new subclass of OFS.Folder (as a python product) to do the following: When a user requests /myFolder/index_html, myFolder will search itself, then its list of 'parents', returning the attribute from one of them if they have it, and raising an AttributeError if not. I have had some moderate success by overloading __getattr__ as follows: def __getattr__(self, name): try: return OFS.Folder.Folder.__getattr__(self, name) except: for parent in self.parentList: try: return getattr(parent, name) except AttributeError: pass raise AttributeError, name This works, in the sense that I can "inherit" features from the parents, but I think there are some fundamental flaws in my approach for the following reasons: o I would like for the user to still be able to create attributes in my folder with the same name as one of the attributes in the parents. This does not work, currently. If I define index_html in a "parent" folder and attempt to do the same in a "child", I get a 'The id index_html is invalid - it is already in use.' error. o Whenever I click on a folder which has one or more "parents" in the top-level management interface (http://localhost/manage), I get a NameError for 'n_'. This does not occur, however, when I manage my folder via http://localhost/myFolder/manage. So, my question is, is there any way for me to achieve this behavior without causing the problems above? I am thinking there must be a way to search the parents if AND ONLY IF it is for an incoming web request. I have posted the code to zope.org at: http://www.zope.org/Members/jkhoffman/TransFolder.tgz Once you install the product, click the 'Parents' tab to assign a parent. This thing is barely working, and is one of my first python products, so please don't laugh at me too much. :) If anyone can give me a push in the right direction I would be extremely grateful. --Jeff
On 11/12/99 3:57 PM, Jeff K. Hoffman at jkhoffman@carolina.rr.com wrote:
I am trying to write a new subclass of OFS.Folder (as a python product) to do the following: When a user requests /myFolder/index_html, myFolder will search itself, then its list of 'parents', returning the attribute from one of them if they have it, and raising an AttributeError if not.
Pardon my ignorance, but what exactly does this accomplish that isn't accomplished by Acquisition? Chris -- | Christopher Petrilli Python Powered Digital Creations, Inc. | petrilli@digicool.com http://www.digicool.com
On Fri, 12 Nov 1999, Christopher Petrilli wrote:
On 11/12/99 3:57 PM, Jeff K. Hoffman at jkhoffman@carolina.rr.com wrote:
I am trying to write a new subclass of OFS.Folder (as a python product) to do the following: When a user requests /myFolder/index_html, myFolder will search itself, then its list of 'parents', returning the attribute from one of them if they have it, and raising an AttributeError if not.
Pardon my ignorance, but what exactly does this accomplish that isn't accomplished by Acquisition?
I am trying to build a site as follows: --- / baseline/ index_html content/ paragraph_a paragraph_b images/ image_a image_b variant1/ content/ paragraph_a images/ image_b variant2/ content/ paragraph_b images/ image_a --- Such that navigating to /baseline/index_html shows paragraph_a, paragraph_b, image_a, and image_b. I also need to be able to navigate to /baseline/variant1 and see the same index_html, this time referencing the "overloaded" paragraph_a and image_b. The same for variant2, with paragraph_b and image_a. I have found no obvious way to do this, using acquisition, without flatting my folder hierarchy out as such: --- / baseline/ paragraph_a paragraph_b image_a image_b variant1/ paragraph_a image_b variant2/ paragraph_b image_a --- This is unacceptable, because there are a LOT of paragraph's and images, and I want to divide them up logically using folders. I am evaluating Zope in the hopes of transitioning one of our major web assets (which is currently built on top of our proprietary web development platform, which supports inheritance) to Zope and dropping development on our platform. I am finding it hard to move from an inheritance based model to a purely acquisition based model without making major sacrifices in the design of our site. Am I stupid? Please tell me I'm missing something obvious.
Chris
--Jeff
On Fri, 12 Nov 1999, Jeff K. Hoffman wrote:
/ baseline/ index_html content/ paragraph_a paragraph_b images/ image_a image_b variant1/ content/ paragraph_a images/ image_b variant2/ content/ paragraph_b images/ image_a ---
Such that navigating to /baseline/index_html shows paragraph_a, paragraph_b, image_a, and image_b. I also need to be able to navigate to /baseline/variant1 and see the same index_html, this time referencing the "overloaded" paragraph_a and image_b. The same for variant2, with paragraph_b and image_a.
Assuming index_html is a *DTML Method* I think something like this might work: <dtml-in 'content.objectValues()'> <do something with paragraphs> </dtml-in> similarly for image. Have-a-feeling-I-missed-the-point'ly Pavlos
"Jeff K. Hoffman" wrote:
On Fri, 12 Nov 1999, Christopher Petrilli wrote:
On 11/12/99 3:57 PM, Jeff K. Hoffman at jkhoffman@carolina.rr.com wrote:
I am trying to write a new subclass of OFS.Folder (as a python product) to do the following: When a user requests /myFolder/index_html, myFolder will search itself, then its list of 'parents', returning the attribute from one of them if they have it, and raising an AttributeError if not.
Pardon my ignorance, but what exactly does this accomplish that isn't accomplished by Acquisition?
I am trying to build a site as follows:
--- / baseline/ index_html content/ paragraph_a paragraph_b images/ image_a image_b variant1/ content/ paragraph_a images/ image_b variant2/ content/ paragraph_b images/ image_a ---
Such that navigating to /baseline/index_html shows paragraph_a, paragraph_b, image_a, and image_b. I also need to be able to navigate to /baseline/variant1 and see the same index_html, this time referencing the "overloaded" paragraph_a and image_b. The same for variant2, with paragraph_b and image_a.
I have found no obvious way to do this, using acquisition, without flatting my folder hierarchy out as such:
(snip)
This is unacceptable, because there are a LOT of paragraph's and images, and I want to divide them up logically using folders.
Interesting. The organizational approach you've taken defeats acquisition. I'll have to think about this (and decide if I care :).
I am evaluating Zope in the hopes of transitioning one of our major web assets (which is currently built on top of our proprietary web development platform, which supports inheritance) to Zope and dropping development on our platform. I am finding it hard to move from an inheritance based model to a purely acquisition based model without making major sacrifices in the design of our site.
Zope supports both acquisition and inheritence. Have you looked at ZClasses? ZClasses were introduced specifically to provide inheritence. We didn't provide inheritence originally, because we thought it was beyond "content- managers", which were the target audience of Principia, the predecessor of Zope. We found, however, that alot of people were mis-using acquisition to achieve the effects of inheritence.
Am I stupid?
No. :)
Please tell me I'm missing something obvious.
I think ZClasses will give you what you want. Jim -- Jim Fulton mailto:jim@digicool.com Python Powered! Technical Director (888) 344-4332 http://www.python.org Digital Creations http://www.digicool.com http://www.zope.org Under US Code Title 47, Sec.227(b)(1)(C), Sec.227(a)(2)(B) This email address may not be added to any commercial mail list with out my permission. Violation of my privacy with advertising or SPAM will result in a suit for a MINIMUM of $500 damages/incident, $1500 for repeats.
On Fri, 12 Nov 1999, Christopher Petrilli wrote:
On 11/12/99 3:57 PM, Jeff K. Hoffman at jkhoffman@carolina.rr.com wrote:
I am trying to write a new subclass of OFS.Folder (as a python product) to do the following: When a user requests /myFolder/index_html, myFolder will search itself, then its list of 'parents', returning the attribute from one of them if they have it, and raising an AttributeError if not.
Pardon my ignorance, but what exactly does this accomplish that isn't accomplished by Acquisition?
Basically, it lets you acquire from a fixed set of parents instead of the entire aquisition path. I'm battling this out for behaviours as well. Another way to think of this is mix-in classes working within the user-space instead of zclass space. Cheers, Anthony Pfrunder
On Fri, 12 Nov 1999, Jeff K. Hoffman wrote:
Hello, everyone.
So, my question is, is there any way for me to achieve this behavior without causing the problems above? I am thinking there must be a way to search the parents if AND ONLY IF it is for an incoming web request.
I'm in the middle of doing this too. I have found that it is better to append / delete from the _ namespace instead of overriding the __getattr__. This way, your meta-dictionary (_ namespace) can perform the right action. Also, it can ignore "writes" and hence avoid the addition problem. I'll post my code once I get it working correctly. BIG WARNING: don't make an attribute in your base class the same name as an exisiting one in the ZClass or you'll run into big problems. Cheers, Anthony Pfrunder
"Jeff K. Hoffman" wrote:
Hello, everyone.
I am trying to write a new subclass of OFS.Folder (as a python product) to do the following: When a user requests /myFolder/index_html, myFolder will search itself, then its list of 'parents', returning the attribute from one of them if they have it, and raising an AttributeError if not.
I have had some moderate success by overloading __getattr__ as follows:
def __getattr__(self, name): try: return OFS.Folder.Folder.__getattr__(self, name) except: for parent in self.parentList: try: return getattr(parent, name) except AttributeError: pass raise AttributeError, name
Never override __getattr__ on persistent objects. __getattr__ is already overridden by the persistence machinery and overriding it yourself will cause big problems. You can accomplish the same thing by overriding __getitem__, being careful to include (or call) the base __getitem__ inherited from ObjectManager. When publishing a URL, Zope tries __bobo_traverse__, then __getattr__, then __getitem__. If you *don't* want to acquire, you will also need to mix-in Acquisition.Explicit, before Folder (or ObjectManager). (snip) Jim -- Jim Fulton mailto:jim@digicool.com Python Powered! Technical Director (888) 344-4332 http://www.python.org Digital Creations http://www.digicool.com http://www.zope.org Under US Code Title 47, Sec.227(b)(1)(C), Sec.227(a)(2)(B) This email address may not be added to any commercial mail list with out my permission. Violation of my privacy with advertising or SPAM will result in a suit for a MINIMUM of $500 damages/incident, $1500 for repeats.
participants (5)
-
Anthony Pfrunder -
Christopher Petrilli -
Jeff K. Hoffman -
Jim Fulton -
Pavlos Christoforou