Search code examples
pythonlxml.objectify

dir(element) returns non-existing element. Trying to use getattr(element, ...) fails


Basically what i do is:

attrs = dir(oe)
for attr in attrs:
  attr_obj = getattr(oe, attr)

  .... more code ...

but the getattr call fails with: AttributeError: no such child: comment

oe is an ObjectifiedElement of the lxml.objectify library.

When i look into oe with PyCharm it shows the comment attribute but also fails to resolve it.

What is going on here? How can this attribute be shown by dir when it does not exist?


Solution

  • I'm no expert but lxml maybe redefining __getattr__ . From their source code:

    def __getattr__(self, tag):
        u"""Return the (first) child with the given tag name.  If no namespace
        is provided, the child will be looked up in the same one as self.
        """
        if is_special_method(tag):
            return object.__getattr__(self, tag)
        return _lookupChildOrRaise(self, tag)
    

    see https://github.com/lxml/lxml/blob/master/src/lxml/lxml.objectify.pyx

    Moreover, about the dir method, you have:

    dir([object]) Without arguments, return the list of names in the current local scope. With an argument, attempt to return a list of valid attributes for that object.

    If the object has a method named dir(), this method will be called and must return the list of attributes. This allows objects that implement a custom getattr() or getattribute() function to customize the way dir() reports their attributes.

    If the object does not provide dir(), the function tries its best to gather information from the object’s dict attribute, if defined, and from its type object. The resulting list is not necessarily complete, and may be inaccurate when the object has a custom getattr().

    see https://docs.python.org/2/library/functions.html#dir