summaryrefslogtreecommitdiffstats
path: root/Lib/distutils/core.py
diff options
context:
space:
mode:
authorGreg Ward <gward@python.net>1999-04-04 02:58:07 (GMT)
committerGreg Ward <gward@python.net>1999-04-04 02:58:07 (GMT)
commit06ca948029492e277896e06fba3d9255ed2430c3 (patch)
tree6021675c5e62bcb12281cea33c7ec6ff8064f1d4 /Lib/distutils/core.py
parente765a3bb61073c4a08acb863e2c897aa2c5bb1db (diff)
downloadcpython-06ca948029492e277896e06fba3d9255ed2430c3.zip
cpython-06ca948029492e277896e06fba3d9255ed2430c3.tar.gz
cpython-06ca948029492e277896e06fba3d9255ed2430c3.tar.bz2
Added all the "external action" methods (to make handling the verbose
and dry-run flags consistently painless): 'execute()', 'mkpath()', 'copy_file()', 'copy_tree()', 'make_file()', and stub for 'make_files()' (not sure yet if it's useful).
Diffstat (limited to 'Lib/distutils/core.py')
-rw-r--r--Lib/distutils/core.py132
1 files changed, 131 insertions, 1 deletions
diff --git a/Lib/distutils/core.py b/Lib/distutils/core.py
index 3a7443c..980ba5b 100644
--- a/Lib/distutils/core.py
+++ b/Lib/distutils/core.py
@@ -10,10 +10,11 @@ may be subclassed by clients for still more flexibility)."""
__rcsid__ = "$Id$"
-import sys
+import sys, os
import string, re
from distutils.errors import *
from distutils.fancy_getopt import fancy_getopt
+from distutils import util
# This is not *quite* the same as a Python NAME; I don't allow leading
# underscores. The fact that they're very similar is no coincidence...
@@ -594,4 +595,133 @@ class Command:
self.distribution.run_command (command)
+
+ # -- External world manipulation -----------------------------------
+
+ def execute (self, func, args, msg=None, level=1):
+ """Perform some action that affects the outside world (eg.
+ by writing to the filesystem). Such actions are special because
+ they should be disabled by the "dry run" flag (carried around by
+ the Command's Distribution), and should announce themselves if
+ the current verbosity level is high enough. This method takes
+ care of all that bureaucracy for you; all you have to do is
+ supply the funtion to call and an argument tuple for it (to
+ embody the "external action" being performed), a message to
+ print if the verbosity level is high enough, and an optional
+ verbosity threshold."""
+
+
+ # Generate a message if we weren't passed one
+ if msg is None:
+ msg = "%s %s" % (func.__name__, `args`)
+ if msg[-2:] == ',)': # correct for singleton tuple
+ msg = msg[0:-2] + ')'
+
+ # Print it if verbosity level is high enough
+ self.announce (msg, level)
+
+ # And do it, as long as we're not in dry-run mode
+ if not self.distribution.dry_run:
+ apply (func, args)
+
+ # execute()
+
+
+ def mkpath (self, name, mode=0777):
+ util.mkpath (name, mode,
+ self.distribution.verbose, self.distribution.dry_run)
+
+
+ def copy_file (self, infile, outfile,
+ preserve_mode=1, preserve_times=1, update=1, level=1):
+ """Copy a file respecting verbose and dry-run flags."""
+
+ util.copy_file (infile, outfile,
+ preserve_mode, preserve_times,
+ update, self.distribution.verbose >= level,
+ self.distribution.dry_run)
+
+
+ def copy_tree (self, infile, outfile,
+ preserve_mode=1, preserve_times=1, preserve_symlinks=0,
+ update=1, level=1):
+ """Copy an entire directory tree respecting verbose and dry-run
+ flags."""
+
+ util.copy_tree (infile, outfile,
+ preserve_mode, preserve_times, preserve_symlinks,
+ update, self.distribution.verbose >= level,
+ self.distribution.dry_run)
+
+
+ def make_file (self, infiles, outfile, func, args,
+ exec_msg=None, skip_msg=None, level=1):
+
+ """Special case of 'execute()' for operations that process one or
+ more input files and generate one output file. Works just like
+ 'execute()', except the operation is skipped and a different
+ message printed if 'outfile' already exists and is newer than
+ all files listed in 'infiles'."""
+
+
+ if exec_msg is None:
+ exec_msg = "generating %s from %s" % \
+ (outfile, string.join (infiles, ', '))
+ if skip_msg is None:
+ skip_msg = "skipping %s (inputs unchanged)" % outfile
+
+
+ # Allow 'infiles' to be a single string
+ if type (infiles) is StringType:
+ infiles = (infiles,)
+ elif type (infiles) not in (ListType, TupleType):
+ raise TypeError, \
+ "'infiles' must be a string, or a list or tuple of strings"
+
+ # XXX this stuff should probably be moved off to a function
+ # in 'distutils.util'
+ from stat import *
+
+ if os.path.exists (outfile):
+ out_mtime = os.stat (outfile)[ST_MTIME]
+
+ # Loop over all infiles. If any infile is newer than outfile,
+ # then we'll have to regenerate outfile
+ for f in infiles:
+ in_mtime = os.stat (f)[ST_MTIME]
+ if in_mtime > out_mtime:
+ runit = 1
+ break
+ else:
+ runit = 0
+
+ else:
+ runit = 1
+
+ # If we determined that 'outfile' must be regenerated, then
+ # perform the action that presumably regenerates it
+ if runit:
+ self.execute (func, args, exec_msg, level)
+
+ # Otherwise, print the "skip" message
+ else:
+ self.announce (skip_msg, level)
+
+ # make_file ()
+
+
+# def make_files (self, infiles, outfiles, func, args,
+# exec_msg=None, skip_msg=None, level=1):
+
+# """Special case of 'execute()' for operations that process one or
+# more input files and generate one or more output files. Works
+# just like 'execute()', except the operation is skipped and a
+# different message printed if all files listed in 'outfiles'
+# already exist and are newer than all files listed in
+# 'infiles'."""
+
+# pass
+
+
+
# end class Command