summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSteven Knight <knight@baldmt.com>2004-10-20 23:59:50 (GMT)
committerSteven Knight <knight@baldmt.com>2004-10-20 23:59:50 (GMT)
commit3e52ca38ff11bf7515dbeb05af362f370479bfb4 (patch)
tree831d26e0cdc9a858e043836ee1b1aaefafe5a9ca
parent8bafc9f80b4f1d46a32cc2eb7d5200979f465c6c (diff)
downloadSCons-3e52ca38ff11bf7515dbeb05af362f370479bfb4.zip
SCons-3e52ca38ff11bf7515dbeb05af362f370479bfb4.tar.gz
SCons-3e52ca38ff11bf7515dbeb05af362f370479bfb4.tar.bz2
Allow explicit target_factory=Dir with Builders that make a directory to override the default, implicit make-a-directory Builder..
-rw-r--r--doc/man/scons.12
-rw-r--r--src/CHANGES.txt3
-rw-r--r--src/engine/SCons/Builder.py4
-rw-r--r--src/engine/SCons/BuilderTests.py2
-rw-r--r--src/engine/SCons/Node/FS.py1
-rw-r--r--src/engine/SCons/Node/NodeTests.py13
-rw-r--r--src/engine/SCons/Node/__init__.py9
-rw-r--r--test/Dir.py16
8 files changed, 47 insertions, 3 deletions
diff --git a/doc/man/scons.1 b/doc/man/scons.1
index f21e00b..b94d680 100644
--- a/doc/man/scons.1
+++ b/doc/man/scons.1
@@ -7655,7 +7655,7 @@ Example:
MakeDirectoryBuilder = Builder(action=my_mkdir, target_factory=Dir)
env = Environment()
env.Append(BUILDERS = {'MakeDirectory':MakeDirectoryBuilder})
-env.MakeDirectory('new_directory')
+env.MakeDirectory('new_directory', [])
.EE
.IP source_factory
diff --git a/src/CHANGES.txt b/src/CHANGES.txt
index 8e0a1ce..5a4062f 100644
--- a/src/CHANGES.txt
+++ b/src/CHANGES.txt
@@ -97,6 +97,9 @@ RELEASE 0.97 - XXX
- Packaging build fix: Rebuild the files that are use to report the
--version of SCons whenever the development version number changes.
+ - Fix the ability to specify a target_factory of Dir() to a Builder,
+ which the default create-a-directory Builder was interfering with.
+
From Clive Levinson:
- Make ParseConfig() recognize and add -mno-cygwin to $LINKFLAGS and
diff --git a/src/engine/SCons/Builder.py b/src/engine/SCons/Builder.py
index e9d4e11..6afff58 100644
--- a/src/engine/SCons/Builder.py
+++ b/src/engine/SCons/Builder.py
@@ -284,7 +284,7 @@ def _init_nodes(builder, env, overrides, executor_kw, tlist, slist):
for t in tlist:
if t.side_effect:
raise UserError, "Multiple ways to build the same target were specified for: %s" % str(t)
- if t.has_builder():
+ if t.has_explicit_builder():
if not t.env is None and not t.env is env:
t_contents = t.builder.action.get_contents(tlist, slist, t.env)
contents = t.builder.action.get_contents(tlist, slist, env)
@@ -412,6 +412,7 @@ class BuilderBase:
single_source = 0,
name = None,
chdir = _null,
+ is_explicit = 1,
**overrides):
if __debug__: logInstanceCreation(self, 'BuilderBase')
self.action = SCons.Action.Action(action)
@@ -453,6 +454,7 @@ class BuilderBase:
self.executor_kw = {}
if not chdir is _null:
self.executor_kw['chdir'] = chdir
+ self.is_explicit = is_explicit
def __nonzero__(self):
raise InternalError, "Do not test for the Node.builder attribute directly; use Node.has_builder() instead"
diff --git a/src/engine/SCons/BuilderTests.py b/src/engine/SCons/BuilderTests.py
index a67d22a..2075bf0 100644
--- a/src/engine/SCons/BuilderTests.py
+++ b/src/engine/SCons/BuilderTests.py
@@ -140,6 +140,8 @@ class MyNode_without_target_from_source:
self.builder = builder
def has_builder(self):
return not self.builder is None
+ def has_explicit_builder(self):
+ return not self.builder is None and self.builder.is_explicit
def env_set(self, env, safe=0):
self.env = env
def add_source(self, source):
diff --git a/src/engine/SCons/Node/FS.py b/src/engine/SCons/Node/FS.py
index 2bd68e1..883b82c 100644
--- a/src/engine/SCons/Node/FS.py
+++ b/src/engine/SCons/Node/FS.py
@@ -194,6 +194,7 @@ def get_MkdirBuilder():
MkdirBuilder = SCons.Builder.Builder(action = Mkdir,
env = None,
explain = None,
+ is_explicit = None,
name = "MkdirBuilder")
return MkdirBuilder
diff --git a/src/engine/SCons/Node/NodeTests.py b/src/engine/SCons/Node/NodeTests.py
index f8cd62b..ce67781 100644
--- a/src/engine/SCons/Node/NodeTests.py
+++ b/src/engine/SCons/Node/NodeTests.py
@@ -93,10 +93,11 @@ class Environment:
self._dict.update(dict)
class Builder:
- def __init__(self):
+ def __init__(self, is_explicit=1):
self.env = Environment()
self.overrides = {}
self.action = MyAction()
+ self.is_explicit = is_explicit
def targets(self, t):
return [t]
def get_actions(self):
@@ -314,6 +315,16 @@ class NodeTestCase(unittest.TestCase):
n1.builder_set(Builder())
assert n1.has_builder() == 1
+ def test_has_explicit_builder(self):
+ """Test the has_explicit_builder() method
+ """
+ n1 = SCons.Node.Node()
+ assert not n1.has_explicit_builder()
+ n1.builder_set(Builder(is_explicit=1))
+ assert n1.has_explicit_builder()
+ n1.builder_set(Builder(is_explicit=None))
+ assert not n1.has_explicit_builder()
+
def test_multiple_side_effect_has_builder(self):
"""Test the multiple_side_effect_has_builder() method
"""
diff --git a/src/engine/SCons/Node/__init__.py b/src/engine/SCons/Node/__init__.py
index 338df07..38cff92 100644
--- a/src/engine/SCons/Node/__init__.py
+++ b/src/engine/SCons/Node/__init__.py
@@ -307,6 +307,15 @@ class Node:
b = self.builder
return not b is None
+ def has_explicit_builder(self):
+ """Return whether this Node has an explicit builder
+
+ This allows an internal Builder created by SCons to be marked
+ non-explicit, so that it can be overridden by an explicit
+ builder that the user supplies (the canonical example being
+ directories)."""
+ return self.has_builder() and self.builder.is_explicit
+
multiple_side_effect_has_builder = has_builder
def is_derived(self):
diff --git a/test/Dir.py b/test/Dir.py
index 5c4eaa3..d7ec9ae 100644
--- a/test/Dir.py
+++ b/test/Dir.py
@@ -55,4 +55,20 @@ bbb_bbb
scons: `.' is up to date.
"""))
+
+
+test.write('SConstruct', """\
+import os
+def my_mkdir(target=None, source=None, env=None):
+ os.mkdir(str(target[0]))
+
+MDBuilder = Builder(action=my_mkdir, target_factory=Dir)
+env = Environment()
+env.Append(BUILDERS = {'MD':MDBuilder})
+env.MD(target='sub1', source=['SConstruct'])
+env.MD(target='sub2', source=['SConstruct'], OVERRIDE='foo')
+""")
+
+test.run()
+
test.pass_test()