an automatic way to do that step with Python as well (PP4E\Internet\Ftp\upload-
flat.py will do the job). Once you’ve started scripting in earnest, you’ll be amazed at
how much manual labor Python can automate. The next section provides another
prime example.
A Regression Test Script
Mistakes happen. As we’ve seen, Python provides interfaces to a variety of system serv-
ices, along with tools for adding others. Example 6-9 shows some of the more com-
monly used system tools in action. It implements a simple regression test system for
Python scripts—it runs each in a directory of Python scripts with provided input and
command-line arguments, and compares the output of each run to the prior run’s re-
sults. As such, this script can be used as an automated testing system to catch errors
introduced by changes in program source files; in a big system, you might not know
when a fix is really a bug in disguise.
Example 6-9. PP4E\System\Tester\tester.py
"""
################################################################################
Test a directory of Python scripts, passing command-line arguments,
piping in stdin, and capturing stdout, stderr, and exit status to
detect failures and regressions from prior run outputs. The subprocess
module spawns and controls streams (much like os.popen3 in Python 2.X),
and is cross-platform. Streams are always binary bytes in subprocess.
Test inputs, args, outputs, and errors map to files in subdirectories.
This is a command-line script, using command-line arguments for
optional test directory name, and force-generation flag. While we
could package it as a callable function, the fact that its results
are messages and output files makes a call/return model less useful.
Suggested enhancement: could be extended to allow multiple sets
of command-line arguments and/or inputs per test script, to run a
script multiple times (glob for multiple ".in*" files in Inputs?).
Might also seem simpler to store all test files in same directory
with different extensions, but this could grow large over time.
Could also save both stderr and stdout to Errors on failures, but
I prefer to have expected/actual output in Outputs on regressions.
################################################################################
"""
import os, sys, glob, time
from subprocess import Popen, PIPE
configuration args
testdir = sys.argv[1] if len(sys.argv) > 1 else os.curdir
forcegen = len(sys.argv) > 2
print('Start tester:', time.asctime())
print('in', os.path.abspath(testdir))
A Regression Test Script | 297