[pygtk] cleaner module reload?

Skip Montanaro skip at pobox.com
Fri Aug 13 05:03:58 WST 2004


    >> try:
    >>     gobject.type_register(foo)
    >> except RuntimeError:
    >>     pass
    >> 
    >> This works but seems "unclean".  (I've been using Python for ten
    >> years or

    Johan> I'm not I can see why raising a RuntimeError from a library like
    Johan> PyGTK is considered unclean.

Like I said, I've been using Python for about ten years and never needed to
catch RuntimeError.  I've just never seen it used in a situation where you
might want to recover.  We're dealing with types and values.  I would expect
a TypeError (type that's already registered) or ValueError (a "value" of
gobject.GObject that's already registered) to be raised here.

    Johan> When are RuntimeError exceptions supposed to be raised?

Rarely, if ever, in my experience.  The libref doc states:

     Raised when an error is detected that doesn't fall in any of the other
     categories.

There are so many builtin exceptions that RuntimeError just doesn't get
used.  It's rare that something else doesn't work.  If nothing builtin
works, the usual route is to define a custom exception of some sort, often
as a subclass of Exception, but sometimes as a subclass of another builtin
exception.

    class TypeRegistrationError(TypeError):
        pass

    >> if not gobject.is_registered(foo):
    >>     gobject.type_register(foo)

    Johan> gobject.type_register sets the __gtype__ variable in the class
    Johan> when it's registered, so this should do it:

    Johan>   if not foo.__dict__['__gtype__']:
    Johan>       ...

    Johan> but that's even uglier, so what about using g_type_name and it's
    Johan> python wrapper?

Yes, but this is cleaner:

    if not hasattr(foo, "__gtype__"):
        gobject.type_register(foo)

    Johan>   if gobject.type_name(foo) != 'GObject':
    Johan>       ...

    Johan> Seems to work, but it's still not the nicest way to check this, so you
    Johan> can check if the name is registered:

    Johan>   if not gobject.type_from_name('__main__+foo'):
    Johan>       ...

I think hasattr() is the way to go.  Thanks for the hint that attributes
were added to the class as a side-effect of type registration.

While we're discussing adding attributes during type registration, I did
notice that __gsignals__ is also removed as a side-effect of type
registration.  This is a shame, because it's lost as a nice indicator of the
signals that are defined by this class.  I'm sure there's some way to
introspect this, but it's not something that (for example) pydoc could use.
It took me awhile to realize pydoc wasn't broken when I tried running it on
one of my GObject subclasses.  I couldn't figure one why it didn't tell me
about __gsignals__.  (I should have noticed the addition of __gtype__ there
as well.)

Skip


More information about the pygtk mailing list