I l@ve RuBoard Previous Section Next Section

2.4 The sys Module

On to module details. As mentioned earlier, the sys and os modules form the core of much of Python's system-related toolset. Let's now take a quick, interactive tour through some of the tools in these two modules, before applying them in bigger examples.

2.4.1 Platforms and Versions

Like most modules, sys includes both informational names and functions that take action. For instance, its attributes give us the name of the underlying operating system the platform code is running on, the largest possible integer on this machine, and the version number of the Python interpreter running our code:

C:\...\PP2E\System>python
>>> import sys
>>> sys.platform, sys.maxint, sys.version
('win32', 2147483647, '1.5.2 (#0, Apr 13 1999, 10:51:12) [MSC 32 bit (Intel)]')
>>>
>>> if sys.platform[:3] == 'win': print 'hello windows'
...
hello windows

If you have code that must act differently on different machines, simply test the sys.platform string as done here; although most of Python is cross-platform, nonportable tools are usually wrapped in if tests like the one here. For instance, we'll see later that program launch and low-level console interaction tools vary per platform today -- simply test sys.platform to pick the right tool for the machine your script is running on.

2.4.2 The Module Search Path

The sys module also lets us inspect the module search path both interactively and within a Python program. sys.path is a list of strings representing the true search path in a running Python interpreter. When a module is imported, Python scans this list from left to right, searching for the module's file on each directory named in the list. Because of that, this is the place to look to verify that your search path is really set as intended.[3]

[3] It's not impossible that Python sees PYTHONPATH differently than you do. A syntax error in your system shell configuration files may botch the setting of PYTHONPATH, even if it looks fine to you. On Windows, for example, if a space appears around the = of a DOS set command in your autoexec.bat file (e.g., set NAME = VALUE), you will actually set NAME to an empty string, not VALUE !

The sys.path list is simply initialized from your PYTHONPATH setting plus system defaults, when the interpreter is first started up. In fact, you'll notice quite a few directories that are not on your PYTHONPATH if you inspect sys.path interactively -- it also includes an indicator for the script's home directory (an empty string -- something I'll explain in more detail after we meet os.getcwd), and a set of standard library directories that may vary per installation:

>>> sys.path 
['', 'C:\\PP2ndEd\\examples',  ...plus standard paths deleted...  ] 

Surprisingly, sys.path can actually be changed by a program too -- a script can use list operations like append, del, and the like to configure the search path at runtime. Python always uses the current sys.path setting to import, no matter what you've changed it to be:

>>> sys.path.append(r'C:\mydir') 
>>> sys.path 
['', 'C:\\PP2ndEd\\examples',  ...more deleted... , 'C:\\mydir']

Changing sys.path directly like this is an alternative to setting your PYTHONPATH shell variable, but not a very good one -- changes to sys.path are retained only until the Python process ends, and must be remade every time you start a new Python program or session.

Windows Directory Paths

Because backslashes normally introduce escape code sequences in Python strings, Windows users should be sure to either double up on backslashes when using them in DOS directory path strings (e.g., in "C:\\dir", \\ is an escape sequence that really means \), or use raw string constants to retain backslashes literally (e.g., r"C:\dir").

If you inspect directory paths on Windows (as in the sys.path interaction listing), Python prints double \\ to mean a single \. Technically, you can get away with a single \ in a string if it is followed by a character Python does not recognize as the rest of an escape sequence, but doubles and raw strings are usually easier than memorizing escape code tables.

Also note that most Python library calls accept either forward ( / ) or backward ( \ ) slashes as directory path separators, regardless of the underlying platform. That is, / usually works on Windows too, and aids in making scripts portable to Unix. Tools in the os and os.path modules, described later in this chapter, further aid in script path portability.

2.4.3 The Loaded Modules Table

The sys module also contains hooks into the interpreter; sys.modules, for example, is a dictionary containing one name:module entry for every module imported in your Python session or program (really, in the calling Python process):

>>> sys.modules
{'os.path': <module 'ntpath' from 'C:\Program Files\Python\Lib\ntpath.pyc'>,...

>>> sys.modules.keys(  )
['os.path', 'os', 'exceptions', '__main__', 'ntpath', 'strop', 'nt', 'sys', 
'__builtin__', 'site', 'signal', 'UserDict', 'string', 'stat']
>>>
>>> sys
<module 'sys' (built-in)>
>>> sys.modules['sys']
<module 'sys' (built-in)>

We might use such a hook to write programs that display or otherwise process all the modules loaded by a program (just iterate over the keys list of sys.modules). sys also exports tools for getting an object's reference count used by Python's garbage collector (getrefcount), checking which modules are built in to this Python (builtin_module_names), and more.

2.4.4 Exception Details

Some of the sys module's attributes allow us to fetch all the information related to the most recently raised Python exception. This is handy if we want to process exceptions in a more generic fashion. For instance, the sys.exc_info function returns the latest exception's type, value, and traceback object:

>>> try:
...     raise IndexError
... except:
...     print sys.exc_info(  )
...
(<class exceptions.IndexError at 7698d0>, <exceptions.IndexError instance at
797140>, <traceback object at 7971a0>)

We might use such information to format our own error message to display in a GUI pop-up window or HTML web page (recall that by default, uncaught exceptions terminate programs with a Python error display). Portability note -- the most recent exception type, value, and traceback objects are also available via other names:

>>> try:
...     raise TypeError, "Bad Thing"
... except:
...     print sys.exc_type, sys.exc_value
...
exceptions.TypeError Bad Thing

But these names represent a single, global exception, and are not specific to a particular thread (threads are covered in the next chapter). If you mean to raise and catch exceptions in multiple threads, exc_info( ) provides thread-specific exception details.

2.4.5 Other sys Module Exports

The sys module exports additional tools we will meet in the context of larger topics and examples later in this chapter and book. For instance:

  • Command-line arguments show up as a list of strings called sys.argv

  • Standard streams are available as stdin, stdout, and stderr

  • Program exit can be forced with sys.exit calls

Since these all lead us to bigger topics, though, we cover them in sections of their own later in this and the next chapters.

    I l@ve RuBoard Previous Section Next Section