From: Thomas Jollans on
On 06/09/2010 11:56 PM, python(a) wrote:
> I'm looking for some suggestions on how to detect exceptions raised
> during common types of file access (os, shutil, codecs, etc.) on a
> cross-platform basis. I'm looking for feedback relative to Python 2.6
> and 2.7 but would also appreciate hearing of any Python 3.x specific
> behaviors.
> Under Python 2.6 for Windows, we're trapping file activity exceptions
> via the following:
> except ( WindowsError, IOError ):
> According to the Exception Hierarchy on this page[1] (and snipped
> below), I suspect that most/all(?) of my file access exceptions "should"
> derive from EnvironmentErrors. In order to make our code more portable,
> should we trap EnvironmentError, IOError, OSError, AND WindowsErrors or
> is that too broad?

Let me answer with an interactive prompt session:

>>> WindowsError
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
NameError: name 'WindowsError' is not defined
>>> isinstance(OSError("error"), EnvironmentError)
>>> try:
.... open("/error/", "r")
.... except (IOError, OSError):
.... print ('caught it!')
caught it!

1. Trying to catch WindowsError is not portable. It doesn't exist on
other platforms.
2. The exception hierarchy is a bog-standard type hierarchy, and you
can use it that way. That's sort of the point.
2. except (IOError, OSError):
should do the trick.
except EnvironmentError:
should also work, but I find the former clearer.

(as for Python versions, I doubt the behaviour has changed in these
respects. In fact, I tried the above with both Python 2.5 and Python 3.1
;-) )

> | +-- EnvironmentError
> | | +-- IOError
> | | +-- OSError
> | | +-- WindowsError (Windows)
> | | +-- VMSError (VMS)
> Part of my confusion/discomfort is the fact that Windows errors are not
> mapped back to the OSError exception, but instead exist in their own
> subclass. I'm curious what makes Windows file access so special that it
> needs its own custom exception class?

I expect that WindowsError and VMSError are used by parts of the
interpreter that call into Windows or VMS APIs, "for historical
reasons". There are probably functions with the same implementation on
Windows and UNIX that would then raise an OSError. I doubt it's ever, to
the programmer, a useful destinction, but it's not a problem either:
just catch OSError instead.

-- Thomas

> Thank you,
> Malcolm
> [1]