Re: [Cheetahtemplate-discuss] Order of name resolution
Brought to you by:
rtyler,
tavis_rudd
From: Mike O. <slu...@gm...> - 2006-08-08 19:27:09
|
On 8/7/06, Andre Louw <al...@ag...> wrote: > > > > > Hi, > > > > What is the reasoning behind the order of checking for an attribute withi= n > an object? The way it is at the moment, if an object implements 'has_key'= , > regardless of whether it's a mapping object, the code tries to resolve th= e > attribute that way, if not found it tries a simple getattr to try and > resolve it. > > > > My problem: I store a proxy to an OSE remote object within a template whe= n > loading it, I need to call a function on this proxy from within the > template. The proxy is implemented somewhat like a mapping object, with t= he > function names as keys in the dictionary, resolving to strings (no idea > why=85). Trying to call the function results in VFN (_valueForName) retur= ning > a string and the actual call to fail. > > > > If the order was to be reversed, i.e check first using a getattr and then > using 'has_key' this will be resolved. What are the chances??? We had to choose one way or the other, and key priority seemed to make the most sense. All objects have attributes, but only objects that have specifically made themselves dict-like have keys. Thus keys are more likely to have the desired value. But Python has no formal way to distinguish dict-like objects from other objects with .__getitem__ (e.g., list-like objects), so we decided on .has_key. That made sense at the time because .has_key was a widely-used method (now "key in dic" is recommended, and .has_key will probably disappear in Python 3.0). It sounds like your proxy object is somewhat defective, in that it defines keys for something not critically useful. I'm not sure if there's a compiler setting to disable key priority (there are tons of compiler settings not well documented) but there is definitely one to disable the NameMapper. =3D=3D=3D=3D x.tmpl =3D=3D=3D=3D ## Cheetah 2.x example. #set dic =3D {"update": 1} #compiler useNameMapper=3DFalse $dic.update #compiler reset $dic.update $getattr($dic, "update") =3D=3D=3D=3D output =3D=3D=3D=3D <built-in method update of dict object at 0xb78fa3e4> 1 <built-in method update of dict object at 0xb78fa3e4> In the first case it finds the dict method. In the second it finds dic['update']. With $getattr it always finds the dict method. Without the NameMapper you *cannot* use the SearchList [1], so you must specify the exact location of the item (usually a local variable or a $self attribute). [1] OK, you can do '$self.searchList[1]["foo"]', but you really shouldn't. --=20 Mike Orr <slu...@gm...> |