Skip to content

Commit

Permalink
Add %(prop:~repl)s to WithProperties: replace unless prop is true
Browse files Browse the repository at this point in the history
Fixes #1011 (finally)
  • Loading branch information
Dustin J. Mitchell committed Oct 26, 2010
1 parent 1704b86 commit 698dc20
Show file tree
Hide file tree
Showing 3 changed files with 66 additions and 15 deletions.
48 changes: 33 additions & 15 deletions master/buildbot/process/properties.py
Expand Up @@ -117,6 +117,7 @@ class PropertyMap:
including the rendering of None as ''.
"""
colon_minus_re = re.compile(r"(.*):-(.*)")
colon_tilde_re = re.compile(r"(.*):~(.*)")
colon_plus_re = re.compile(r"(.*):\+(.*)")
def __init__(self, properties):
# use weakref here to avoid a reference loop
Expand All @@ -126,27 +127,44 @@ def __getitem__(self, key):
properties = self.properties()
assert properties is not None

# %(prop:-repl)s
# if prop exists, use it; otherwise, use repl
mo = self.colon_minus_re.match(key)
if mo:
def colon_minus(mo):
# %(prop:-repl)s
# if prop exists, use it; otherwise, use repl
prop, repl = mo.group(1,2)
if properties.has_key(prop):
rv = properties[prop]
return properties[prop]
else:
rv = repl
else:
return repl

def colon_tilde(mo):
# %(prop:~repl)s
# if prop exists and is true (nonempty), use it; otherwise, use repl
prop, repl = mo.group(1,2)
if properties.has_key(prop) and properties[prop]:
return properties[prop]
else:
return repl

def colon_plus(mo):
# %(prop:+repl)s
# if prop exists, use repl; otherwise, an empty string
mo = self.colon_plus_re.match(key)
if mo:
prop, repl = mo.group(1,2)
if properties.has_key(prop):
rv = repl
else:
rv = ''
prop, repl = mo.group(1,2)
if properties.has_key(prop):
return repl
else:
rv = properties[key]
return ''

for regexp, fn in [
( self.colon_minus_re, colon_minus ),
( self.colon_tilde_re, colon_tilde ),
( self.colon_plus_re, colon_plus ),
]:
mo = regexp.match(key)
if mo:
rv = fn(mo)
break
else:
rv = properties[key]

# translate 'None' to an empty string
if rv is None: rv = ''
Expand Down
27 changes: 27 additions & 0 deletions master/buildbot/test/unit/test_process_properties.py
Expand Up @@ -80,6 +80,32 @@ def testColonMinusUnset(self):
self.assertEqual(self.pm['prop_nosuch:-missing'], 'missing')


def testColonTildeSet(self):
self.assertEqual(self.pm['prop_str:~missing'], 'a-string')

def testColonTildeNone(self):
# None is special-cased *differently* for ~:
self.assertEqual(self.pm['prop_none:~missing'], 'missing')

def testColonTildeZero(self):
self.assertEqual(self.pm['prop_zero:~missing'], 'missing')

def testColonTildeOne(self):
self.assertEqual(self.pm['prop_one:~missing'], 1)

def testColonTildeFalse(self):
self.assertEqual(self.pm['prop_false:~missing'], 'missing')

def testColonTildeTrue(self):
self.assertEqual(self.pm['prop_true:~missing'], True)

def testColonTildeEmpty(self):
self.assertEqual(self.pm['prop_empty:~missing'], 'missing')

def testColonTildeUnset(self):
self.assertEqual(self.pm['prop_nosuch:~missing'], 'missing')


def testColonPlusSet(self):
self.assertEqual(self.pm['prop_str:+present'], 'present')

Expand All @@ -104,6 +130,7 @@ def testColonPlusEmpty(self):
def testColonPlusUnset(self):
self.assertEqual(self.pm['prop_nosuch:+present'], '')


class TestWithProperties(unittest.TestCase):
def setUp(self):
self.props = Properties()
Expand Down
6 changes: 6 additions & 0 deletions master/docs/cfg-buildsteps.texinfo
Expand Up @@ -192,6 +192,12 @@ If @code{propname} exists, substitute its value; otherwise,
substitute @code{replacement}. @code{replacement} may be empty
(@code{%(propname:-)s})

@item propname:~replacement
Like @code{propname:-replacement}, but only substitutes the value
of property @code{propname} if it is something Python regards as "true".
Python considers @code{None}, 0, empty lists, and the empty string to be
false, so such values will be replaced by @code{replacement}.

@item propname:+replacement
If @code{propname} exists, substitute @code{replacement}; otherwise,
substitute an empty string.
Expand Down

0 comments on commit 698dc20

Please sign in to comment.