The heart of SCons is its Build Engine. The SCons Build Engine is a Python module that manages dependencies between external objects such as files or database records. The Build Engine is designed to be interface-neutral and easily embeddable in any software system that needs dependency analysis between updatable objects.
The key parts of the Build Engine architecture are captured in the following quasi-UML diagram:
The point of SCons is to manage
dependencies between arbitrary external objects.
Consequently, the Build Engine does not restrict or specify
the nature of the external objects it manages,
but instead relies on subclass of the Node
class to interact with the external system or systems
(file systems, database management systems)
that maintain the objects being examined or updated.
The Build Engine presents to the software system in which it is embedded a Python API for specifying source (input) and target (output) objects, rules for building/updating objects, rules for scanning objects for dependencies, etc. Above its Python API, the Build Engine is completely interface-independent, and can be encapsulated by any other software that supports embedded Python.
Software that chooses to use the Build Engine
for dependency management
interacts with it
through Construction Environments.
A Construction Environment consists
of a dictionary of environment variables,
and one or more associated
Scanner
objects
and Builder
objects.
The Python API is used to
form these associations.
A Scanner
object specifies
how to examine a type of source object
(C source file, database record)
for dependency information.
A Scanner
object may use
variables from the associated
Construction Environment
to modify how it scans an object:
specifying a search path for included files,
which field in a database record to consult,
etc.
A Builder
object specifies
how to update a type of target object:
executable program, object file, database field, etc.
Like a Scanner
object,
a Builder
object may use
variables from the associated
Construction Environment
to modify how it builds an object:
specifying flags to a compiler,
using a different update function,
etc.
Scanner
and Builder
objects will return one or more
Node
objects that represent external objects.
Node
objects are the means by which the
Build Engine tracks dependencies:
A Node
may represent a source (input) object that
should already exist,
or a target (output) object which may be built,
or both.
The Node
class is sub-classed to
represent external objects of specific type:
files, directories, database fields or records, etc.
Because dependency information, however,
is tracked by the top-level Node
methods and attributes,
dependencies can exist
between nodes representing different external object types.
For example,
building a file could be made
dependent on the value of a given
field in a database record,
or a database table could depend
on the contents of an external file.
The Build Engine uses a Job
class (not displayed)
to manage the actual work of updating external target objects:
spawning commands to build files,
submitting the necessary commands to update a database record,
etc.
The Job
class has sub-classes
to handle differences between spawning
jobs in parallel and serially.
The Build Engine also uses a
Signature
class (not displayed)
to maintain information about whether
an external object is up-to-date.
Target objects with out-of-date signatures
are updated using the appropriate
Builder
object.