Sophie

Sophie

distrib > Mageia > 4 > i586 > by-pkgid > 74a079f60081eb768b37d9cbd7adb753 > files > 132

buildbot-doc-0.8.8-3.mga4.noarch.rpm



<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
  "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">


<html xmlns="http://www.w3.org/1999/xhtml">
  <head>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
    
    <title>Properties &mdash; Buildbot 0.8.8 documentation</title>
    
    <link rel="stylesheet" href="../_static/agogo.css" type="text/css" />
    <link rel="stylesheet" href="../_static/pygments.css" type="text/css" />
    
    <script type="text/javascript">
      var DOCUMENTATION_OPTIONS = {
        URL_ROOT:    '../',
        VERSION:     '0.8.8',
        COLLAPSE_INDEX: false,
        FILE_SUFFIX: '.html',
        HAS_SOURCE:  true
      };
    </script>
    <script type="text/javascript" src="../_static/jquery.js"></script>
    <script type="text/javascript" src="../_static/underscore.js"></script>
    <script type="text/javascript" src="../_static/doctools.js"></script>
    <link rel="shortcut icon" href="../_static/buildbot.ico"/>
    <link rel="top" title="Buildbot 0.8.8 documentation" href="../index.html" />
    <link rel="up" title="Configuration" href="configuration.html" />
    <link rel="next" title="Build Steps" href="cfg-buildsteps.html" />
    <link rel="prev" title="Build Factories" href="cfg-buildfactories.html" /> 
  </head>
  <body>
    <div class="header-wrapper">
      <div class="header">
          <p class="logo"><a href="../index.html">
            <img class="logo" src="../_static/header-text-transparent.png" alt="Logo"/>
          </a></p>
        <div class="headertitle"><a
          href="../index.html">Buildbot 0.8.8 documentation</a></div>
        <div class="rel">
          <a href="cfg-buildfactories.html" title="Build Factories"
             accesskey="P">previous</a> |
          <a href="cfg-buildsteps.html" title="Build Steps"
             accesskey="N">next</a> |
          <a href="../py-modindex.html" title="Python Module Index"
             >modules</a> |
          <a href="../genindex.html" title="General Index"
             accesskey="I">index</a>
        </div>
       </div>
    </div>

    <div class="content-wrapper">
      <div class="content">
        <div class="document">
            
      <div class="documentwrapper">
        <div class="bodywrapper">
          <div class="body">
            
  <div class="section" id="properties">
<span id="index-0"></span><span id="id1"></span><h1>Properties<a class="headerlink" href="#properties" title="Permalink to this headline">¶</a></h1>
<p>Build properties are a generalized way to provide configuration information to
build steps; see <a class="reference internal" href="concepts.html#build-properties"><em>Build Properties</em></a> for the conceptual overview of
properties.</p>
<p>Some build properties come from external sources and are set before the build
begins; others are set during the build, and available for later steps.  The
sources for properties are:</p>
<ul class="simple">
<li><a class="reference internal" href="cfg-global.html#cfg-properties" title="properties"><tt class="xref bb bb-cfg docutils literal"><span class="pre">global</span> <span class="pre">configuration</span></tt></a> -- These properties apply to all
builds.</li>
<li><a class="reference internal" href="cfg-schedulers.html#configuring-schedulers"><em>schedulers</em></a> -- A scheduler can specify
properties that become available to all builds it starts.</li>
<li><a class="reference internal" href="cfg-changesources.html#change-sources"><em>changes</em></a> -- A change can have properties attached to
it, supplying extra information gathered by the change source.  This is most
commonly used with the <a class="reference internal" href="cmdline.html#cmdline-sendchange" title="sendchange"><tt class="xref bb bb-cmdline docutils literal"><span class="pre">sendchange</span></tt></a> command.</li>
<li><a class="reference internal" href="cfg-statustargets.html#status-WebStatus" title="WebStatus"><tt class="xref bb bb-status docutils literal"><span class="pre">forced</span> <span class="pre">builds</span></tt></a> -- The &quot;Force Build&quot; form allows users
to specify properties</li>
<li><a class="reference internal" href="cfg-buildslaves.html#cfg-slaves" title="slaves"><tt class="xref bb bb-cfg docutils literal"><span class="pre">buildslaves</span></tt></a> -- A buildslave can pass properties on to
the builds it performs.</li>
<li><a class="reference internal" href="#common-build-properties"><em>builds</em></a> -- A build automatically sets a
number of properties on itself.</li>
<li><a class="reference internal" href="cfg-builders.html#cfg-builders" title="builders"><tt class="xref bb bb-cfg docutils literal"><span class="pre">builders</span></tt></a> -- A builder can set properties on all the
builds it runs.</li>
<li><a class="reference internal" href="cfg-buildsteps.html#build-steps"><em>steps</em></a> -- The steps of a build can set properties that are available to subsequent steps.
In particular, source steps set the <cite>got_revision</cite> property.</li>
</ul>
<p>If the same property is supplied in multiple places, the final appearance takes
precedence.  For example, a property set in a builder configuration will
override one supplied by a scheduler.</p>
<p>Properties are stored internally in JSON format, so they are limited to basic
types of data: numbers, strings, lists, and dictionaries.</p>
<div class="section" id="common-build-properties">
<span id="index-1"></span><span id="id2"></span><h2>Common Build Properties<a class="headerlink" href="#common-build-properties" title="Permalink to this headline">¶</a></h2>
<p>The following build properties are set when the build is started, and
are available to all steps.</p>
<dl class="docutils" id="index-2">
<dt><tt class="docutils literal"><span class="pre">got_revision</span></tt></dt>
<dd><p class="first">This property is set when a <tt class="xref py py-class docutils literal"><span class="pre">Source</span></tt> step checks out the source tree, and provides the revision that was actually obtained from the VC system.
In general this should be the same as <tt class="docutils literal"><span class="pre">revision</span></tt>, except for non-absolute sourcestamps, where <tt class="docutils literal"><span class="pre">got_revision</span></tt> indicates what revision was current when the checkout was performed.
This can be used to rebuild the same source code later.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">For some VC systems (Darcs in particular), the revision is a
large string containing newlines, and is not suitable for interpolation
into a filename.</p>
</div>
<p class="last">For multi-codebase builds (where codebase is not the default <cite>''</cite>), this property is a dictionary, keyed by codebase.</p>
</dd>
</dl>
<dl class="docutils" id="index-3">
<dt><tt class="docutils literal"><span class="pre">buildername</span></tt></dt>
<dd>This is a string that indicates which <tt class="xref py py-class docutils literal"><span class="pre">Builder</span></tt> the build was a part of.
The combination of buildername and buildnumber uniquely identify a
build.</dd>
</dl>
<dl class="docutils" id="index-4">
<dt><tt class="docutils literal"><span class="pre">buildnumber</span></tt></dt>
<dd>Each build gets a number, scoped to the <tt class="xref py py-class docutils literal"><span class="pre">Builder</span></tt> (so the first build
performed on any given <tt class="xref py py-class docutils literal"><span class="pre">Builder</span></tt> will have a build number of 0). This
integer property contains the build's number.</dd>
</dl>
<dl class="docutils" id="index-5">
<dt><tt class="docutils literal"><span class="pre">slavename</span></tt></dt>
<dd>This is a string which identifies which buildslave the build is
running on.</dd>
</dl>
<dl class="docutils" id="index-6">
<dt><tt class="docutils literal"><span class="pre">scheduler</span></tt></dt>
<dd>If the build was started from a scheduler, then this property will
contain the name of that scheduler.</dd>
<dt><tt class="docutils literal"><span class="pre">workdir</span></tt></dt>
<dd>The absolute path of the base working directory on the slave, of the current
builder.</dd>
</dl>
<p id="index-7">For single codebase builds, where the codebase is <cite>''</cite>, the following <a class="reference internal" href="#source-stamp-attributes"><em>Source Stamp Attributes</em></a> are also available as properties: <tt class="docutils literal"><span class="pre">branch</span></tt>, <tt class="docutils literal"><span class="pre">revision</span></tt>, <tt class="docutils literal"><span class="pre">repository</span></tt>, and <tt class="docutils literal"><span class="pre">project</span></tt> .</p>
</div>
<div class="section" id="source-stamp-attributes">
<span id="id3"></span><h2>Source Stamp Attributes<a class="headerlink" href="#source-stamp-attributes" title="Permalink to this headline">¶</a></h2>
<p id="index-8"><tt class="docutils literal"><span class="pre">branch</span></tt>
<tt class="docutils literal"><span class="pre">revision</span></tt>
<tt class="docutils literal"><span class="pre">repository</span></tt>
<tt class="docutils literal"><span class="pre">project</span></tt>
<tt class="docutils literal"><span class="pre">codebase</span></tt></p>
<blockquote>
<div>For details of these attributes see <a class="reference internal" href="concepts.html"><em>Concepts</em></a>.</div></blockquote>
<p><tt class="docutils literal"><span class="pre">changes</span></tt></p>
<blockquote>
<div>This attribute is a list of dictionaries reperesnting the changes that make up this sourcestamp.</div></blockquote>
<p><tt class="docutils literal"><span class="pre">has_patch</span></tt>
<tt class="docutils literal"><span class="pre">patch_level</span></tt>
<tt class="docutils literal"><span class="pre">patch_body</span></tt>
<tt class="docutils literal"><span class="pre">patch_subdir</span></tt>
<tt class="docutils literal"><span class="pre">patch_author</span></tt>
<tt class="docutils literal"><span class="pre">patch_comment</span></tt></p>
<blockquote>
<div>These attributes are set if the source stamp was created by a <a class="reference internal" href="cfg-schedulers.html#try-schedulers"><em>try scheduler</em></a>.</div></blockquote>
</div>
<div class="section" id="using-properties-in-steps">
<h2>Using Properties in Steps<a class="headerlink" href="#using-properties-in-steps" title="Permalink to this headline">¶</a></h2>
<p>For the most part, properties are used to alter the behavior of build steps
during a build.  This is done by annotating the step definition in
<tt class="docutils literal"><span class="pre">master.cfg</span></tt> with placeholders.  When the step is executed, these
placeholders will be replaced using the current values of the build properties.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p>Properties are defined while a build is in progress; their values are
not available when the configuration file is parsed.  This can sometimes
confuse newcomers to Buildbot!  In particular, the following is a common error:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="k">if</span> <span class="n">Property</span><span class="p">(</span><span class="s">&#39;release_train&#39;</span><span class="p">)</span> <span class="o">==</span> <span class="s">&#39;alpha&#39;</span><span class="p">:</span>
    <span class="n">f</span><span class="o">.</span><span class="n">addStep</span><span class="p">(</span><span class="o">...</span><span class="p">)</span>
</pre></div>
</div>
<p class="last">This does not work because the value of the property is not available when
the <tt class="docutils literal"><span class="pre">if</span></tt> statement is executed.  However, Python will not detect this as
an error - you will just never see the step added to the factory.</p>
</div>
<p>You can use build properties in most step parameters.  Please file bugs for any
parameters which do not accept properties.</p>
<div class="section" id="property">
<span id="index-9"></span><span id="id4"></span><h3>Property<a class="headerlink" href="#property" title="Permalink to this headline">¶</a></h3>
<p>The simplest form of annotation is to wrap the property name with
<tt class="xref py py-class docutils literal"><span class="pre">Property</span></tt>:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="kn">from</span> <span class="nn">buildbot.steps.shell</span> <span class="kn">import</span> <span class="n">ShellCommand</span>
<span class="kn">from</span> <span class="nn">buildbot.process.properties</span> <span class="kn">import</span> <span class="n">Property</span>

<span class="n">f</span><span class="o">.</span><span class="n">addStep</span><span class="p">(</span><span class="n">ShellCommand</span><span class="p">(</span><span class="n">command</span><span class="o">=</span><span class="p">[</span> <span class="s">&#39;echo&#39;</span><span class="p">,</span> <span class="s">&#39;buildername:&#39;</span><span class="p">,</span> <span class="n">Property</span><span class="p">(</span><span class="s">&#39;buildername&#39;</span><span class="p">)</span> <span class="p">]))</span>
</pre></div>
</div>
<p>You can specify a default value by passing a <tt class="docutils literal"><span class="pre">default</span></tt> keyword argument:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="n">f</span><span class="o">.</span><span class="n">addStep</span><span class="p">(</span><span class="n">ShellCommand</span><span class="p">(</span><span class="n">command</span><span class="o">=</span><span class="p">[</span> <span class="s">&#39;echo&#39;</span><span class="p">,</span> <span class="s">&#39;warnings:&#39;</span><span class="p">,</span>
                                 <span class="n">Property</span><span class="p">(</span><span class="s">&#39;warnings&#39;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="s">&#39;none&#39;</span><span class="p">)</span> <span class="p">]))</span>
</pre></div>
</div>
<p>The default value is used when the property doesn't exist, or when the value is
something Python regards as <tt class="docutils literal"><span class="pre">False</span></tt>. The <tt class="docutils literal"><span class="pre">defaultWhenFalse</span></tt> argument can be
set to <tt class="docutils literal"><span class="pre">False</span></tt> to force buildbot to use the default argument only if the
parameter is not set:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="n">f</span><span class="o">.</span><span class="n">addStep</span><span class="p">(</span><span class="n">ShellCommand</span><span class="p">(</span><span class="n">command</span><span class="o">=</span><span class="p">[</span> <span class="s">&#39;echo&#39;</span><span class="p">,</span> <span class="s">&#39;warnings:&#39;</span><span class="p">,</span>
                 <span class="n">Property</span><span class="p">(</span><span class="s">&#39;warnings&#39;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="s">&#39;none&#39;</span><span class="p">,</span> <span class="n">defaultWhenFalse</span><span class="o">=</span><span class="bp">False</span><span class="p">)</span> <span class="p">]))</span>
</pre></div>
</div>
<p>The default value can reference other properties, e.g.,</p>
<div class="highlight-python"><div class="highlight"><pre><span class="n">command</span><span class="o">=</span><span class="n">Property</span><span class="p">(</span><span class="s">&#39;command&#39;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="n">Property</span><span class="p">(</span><span class="s">&#39;default-command&#39;</span><span class="p">))</span>
</pre></div>
</div>
</div>
<div class="section" id="interpolate">
<span id="index-10"></span><span id="id5"></span><h3>Interpolate<a class="headerlink" href="#interpolate" title="Permalink to this headline">¶</a></h3>
<p><tt class="xref py py-class docutils literal"><span class="pre">Property</span></tt> can only be used to replace an entire argument: in the
example above, it replaces an argument to <tt class="docutils literal"><span class="pre">echo</span></tt>.  Often, properties need to
be interpolated into strings, instead.  The tool for that job is
<a class="reference internal" href="#interpolate"><em>Interpolate</em></a>.</p>
<p>The more common pattern is to use Python dictionary-style string interpolation by using the <tt class="docutils literal"><span class="pre">%(prop:&lt;propname&gt;)s</span></tt> syntax.
In this form, the property name goes in the parentheses, as above.
A common mistake is to omit the trailing &quot;s&quot;, leading to a rather obscure error from Python (&quot;ValueError: unsupported format character&quot;).</p>
<div class="highlight-python"><div class="highlight"><pre><span class="kn">from</span> <span class="nn">buildbot.steps.shell</span> <span class="kn">import</span> <span class="n">ShellCommand</span>
<span class="kn">from</span> <span class="nn">buildbot.process.properties</span> <span class="kn">import</span> <span class="n">Interpolate</span>
<span class="n">f</span><span class="o">.</span><span class="n">addStep</span><span class="p">(</span><span class="n">ShellCommand</span><span class="p">(</span><span class="n">command</span><span class="o">=</span><span class="p">[</span> <span class="s">&#39;make&#39;</span><span class="p">,</span> <span class="n">Interpolate</span><span class="p">(</span><span class="s">&#39;REVISION=%(prop:got_revision)s&#39;</span><span class="p">),</span>
                                 <span class="s">&#39;dist&#39;</span> <span class="p">]))</span>
</pre></div>
</div>
<p>This example will result in a <tt class="docutils literal"><span class="pre">make</span></tt> command with an argument like
<tt class="docutils literal"><span class="pre">REVISION=12098</span></tt>.</p>
<p id="interpolate-dictstyle">The syntax of dictionary-style interpolation is a selector, followed by a colon, followed by a selector specific key, optionally followed by a colon and a string indicating how to interpret the value produced by the key.</p>
<p>The following selectors are supported.</p>
<dl class="docutils">
<dt><tt class="docutils literal"><span class="pre">prop</span></tt></dt>
<dd>The key is the name of a property.</dd>
<dt><tt class="docutils literal"><span class="pre">src</span></tt></dt>
<dd>The key is a codebase and source stamp attribute, separated by a colon.</dd>
<dt><tt class="docutils literal"><span class="pre">kw</span></tt></dt>
<dd>The key refers to a keyword argument passed to <tt class="docutils literal"><span class="pre">Interpolate</span></tt>.</dd>
</dl>
<p>The following ways of interpreting the value are available.</p>
<dl class="docutils">
<dt><tt class="docutils literal"><span class="pre">-replacement</span></tt></dt>
<dd>If the key exists, substitute its value; otherwise,
substitute <tt class="docutils literal"><span class="pre">replacement</span></tt>. <tt class="docutils literal"><span class="pre">replacement</span></tt> may be empty
(<tt class="docutils literal"><span class="pre">%(prop:propname:-)s</span></tt>). This is the default.</dd>
<dt><tt class="docutils literal"><span class="pre">~replacement</span></tt></dt>
<dd>Like <tt class="docutils literal"><span class="pre">-replacement</span></tt>, but only substitutes the value
of the key if it is something Python regards as <tt class="docutils literal"><span class="pre">True</span></tt>.
Python considers <tt class="docutils literal"><span class="pre">None</span></tt>, 0, empty lists, and the empty string to be
false, so such values will be replaced by <tt class="docutils literal"><span class="pre">replacement</span></tt>.</dd>
<dt><tt class="docutils literal"><span class="pre">+replacement</span></tt></dt>
<dd>If the key exists, substitute <tt class="docutils literal"><span class="pre">replacement</span></tt>; otherwise,
substitute an empty string.</dd>
</dl>
<p><tt class="docutils literal"><span class="pre">?|sub_if_exists|sub_if_missing</span></tt></p>
<dl class="docutils">
<dt><tt class="docutils literal"><span class="pre">#?|sub_if_true|sub_if_false</span></tt></dt>
<dd>Ternary substitution, depending on either the key being present (with
<tt class="docutils literal"><span class="pre">?</span></tt>, similar to <tt class="docutils literal"><span class="pre">+</span></tt>) or being <tt class="docutils literal"><span class="pre">True</span></tt> (with <tt class="docutils literal"><span class="pre">#?</span></tt>, like <tt class="docutils literal"><span class="pre">~</span></tt>).
Notice that there is a pipe immediately following the question mark <em>and</em>
between the two substitution alternatives. The character that follows the
question mark is used as the delimiter between the two alternatives. In the
above examples, it is a pipe, but any character other than <tt class="docutils literal"><span class="pre">(</span></tt> can be used.</dd>
</dl>
<p>Although these are similar to shell substitutions, no other substitutions are currently supported.</p>
<p>Example</p>
<div class="highlight-python"><pre>from buildbot.steps.shell import ShellCommand
from buildbot.process.properties import Interpolate
f.addStep(ShellCommand(command=[ 'make', Interpolate('REVISION=%(prop:got_revision:-%(src::revision:-unknown)s)s')
                                 'dist' ]))</pre>
</div>
<p>In addition, <tt class="docutils literal"><span class="pre">Interpolate</span></tt> supports using positional string interpolation.
Here, <tt class="docutils literal"><span class="pre">%s</span></tt> is used as a placeholder, and the substitutions (which may themselves be placeholders), are given as subsequent arguments:</p>
<div class="highlight-python"><pre>.. note:</pre>
</div>
<blockquote>
<div>Like Python, you can use either positional interpolation <em>or</em>
dictionary-style interpolation, not both.  Thus you cannot use a string
like <tt class="docutils literal"><span class="pre">Interpolate(&quot;foo-%(src::revision)s-%s&quot;,</span> <span class="pre">&quot;branch&quot;)</span></tt>.</div></blockquote>
</div>
<div class="section" id="renderer">
<span id="index-11"></span><span id="id6"></span><h3>Renderer<a class="headerlink" href="#renderer" title="Permalink to this headline">¶</a></h3>
<p>While Interpolate can handle many simple cases, and even some common conditionals, more complex cases are best handled with Python code.
The <tt class="docutils literal"><span class="pre">renderer</span></tt> decorator creates a renderable object that will be replaced with the result of the function, called when the step it's passed to begins.
The function receives an <tt class="xref py py-class docutils literal"><span class="pre">IProperties</span></tt> object, which it can use to examine the values of any and all properties.  For example:</p>
<div class="highlight-python"><pre> @properties.renderer
 def makeCommand(props):
     command = [ 'make' ]
     cpus = props.getProperty('CPUs')
     if cpus:
         command += [ '-j', str(cpus+1) ]
     else:
         command += [ '-j', '2' ]
     command += [ 'all' ]
     return command
f.addStep(ShellCommand(command=makeCommand))</pre>
</div>
<p>You can think of <tt class="docutils literal"><span class="pre">renderer</span></tt> as saying &quot;call this function when the step starts&quot;.</p>
</div>
<div class="section" id="withproperties">
<span id="index-12"></span><span id="id7"></span><h3>WithProperties<a class="headerlink" href="#withproperties" title="Permalink to this headline">¶</a></h3>
<div class="admonition warning">
<p class="first admonition-title">Warning</p>
<p class="last">This placeholder is deprecated. It is an older version of <a class="reference internal" href="#interpolate"><em>Interpolate</em></a>.
It exists for compatibility with older configs.</p>
</div>
<p>The simplest use of this class is with positional string interpolation.  Here,
<tt class="docutils literal"><span class="pre">%s</span></tt> is used as a placeholder, and property names are given as subsequent
arguments:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="kn">from</span> <span class="nn">buildbot.steps.shell</span> <span class="kn">import</span> <span class="n">ShellCommand</span>
<span class="kn">from</span> <span class="nn">buildbot.process.properties</span> <span class="kn">import</span> <span class="n">WithProperties</span>
<span class="n">f</span><span class="o">.</span><span class="n">addStep</span><span class="p">(</span><span class="n">ShellCommand</span><span class="p">(</span>
          <span class="n">command</span><span class="o">=</span><span class="p">[</span><span class="s">&quot;tar&quot;</span><span class="p">,</span> <span class="s">&quot;czf&quot;</span><span class="p">,</span>
                   <span class="n">WithProperties</span><span class="p">(</span><span class="s">&quot;build-</span><span class="si">%s</span><span class="s">-</span><span class="si">%s</span><span class="s">.tar.gz&quot;</span><span class="p">,</span> <span class="s">&quot;branch&quot;</span><span class="p">,</span> <span class="s">&quot;revision&quot;</span><span class="p">),</span>
                   <span class="s">&quot;source&quot;</span><span class="p">]))</span>
</pre></div>
</div>
<p>If this <tt class="xref py py-class docutils literal"><span class="pre">BuildStep</span></tt> were used in a tree obtained from Git, it would
create a tarball with a name like
<tt class="file docutils literal"><span class="pre">build-master-a7d3a333db708e786edb34b6af646edd8d4d3ad9.tar.gz</span></tt>.</p>
<p id="index-13">The more common pattern is to use Python dictionary-style string interpolation
by using the <tt class="docutils literal"><span class="pre">%(propname)s</span></tt> syntax. In this form, the property name goes in
the parentheses, as above.  A common mistake is to omit the trailing &quot;s&quot;,
leading to a rather obscure error from Python (&quot;ValueError: unsupported format
character&quot;).</p>
<div class="highlight-python"><div class="highlight"><pre><span class="kn">from</span> <span class="nn">buildbot.steps.shell</span> <span class="kn">import</span> <span class="n">ShellCommand</span>
<span class="kn">from</span> <span class="nn">buildbot.process.properties</span> <span class="kn">import</span> <span class="n">WithProperties</span>
<span class="n">f</span><span class="o">.</span><span class="n">addStep</span><span class="p">(</span><span class="n">ShellCommand</span><span class="p">(</span><span class="n">command</span><span class="o">=</span><span class="p">[</span> <span class="s">&#39;make&#39;</span><span class="p">,</span> <span class="n">WithProperties</span><span class="p">(</span><span class="s">&#39;REVISION=</span><span class="si">%(got_revision)s</span><span class="s">&#39;</span><span class="p">),</span>
                                 <span class="s">&#39;dist&#39;</span> <span class="p">]))</span>
</pre></div>
</div>
<p>This example will result in a <tt class="docutils literal"><span class="pre">make</span></tt> command with an argument like
<tt class="docutils literal"><span class="pre">REVISION=12098</span></tt>.</p>
<p id="withproperties-dictstyle">The dictionary-style interpolation supports a number of more advanced
syntaxes in the parentheses.</p>
<dl class="docutils">
<dt><tt class="docutils literal"><span class="pre">propname:-replacement</span></tt></dt>
<dd>If <tt class="docutils literal"><span class="pre">propname</span></tt> exists, substitute its value; otherwise,
substitute <tt class="docutils literal"><span class="pre">replacement</span></tt>. <tt class="docutils literal"><span class="pre">replacement</span></tt> may be empty
(<tt class="docutils literal"><span class="pre">%(propname:-)s</span></tt>)</dd>
<dt><tt class="docutils literal"><span class="pre">propname:~replacement</span></tt></dt>
<dd>Like <tt class="docutils literal"><span class="pre">propname:-replacement</span></tt>, but only substitutes the value
of property <tt class="docutils literal"><span class="pre">propname</span></tt> if it is something Python regards as <tt class="docutils literal"><span class="pre">True</span></tt>.
Python considers <tt class="docutils literal"><span class="pre">None</span></tt>, 0, empty lists, and the empty string to be
false, so such values will be replaced by <tt class="docutils literal"><span class="pre">replacement</span></tt>.</dd>
<dt><tt class="docutils literal"><span class="pre">propname:+replacement</span></tt></dt>
<dd>If <tt class="docutils literal"><span class="pre">propname</span></tt> exists, substitute <tt class="docutils literal"><span class="pre">replacement</span></tt>; otherwise,
substitute an empty string.</dd>
</dl>
<p>Although these are similar to shell substitutions, no other
substitutions are currently supported, and <tt class="docutils literal"><span class="pre">replacement</span></tt> in the
above cannot contain more substitutions.</p>
<p>Note: like Python, you can use either positional interpolation <em>or</em>
dictionary-style interpolation, not both. Thus you cannot use a string like
<tt class="docutils literal"><span class="pre">WithProperties(&quot;foo-%(revision)s-%s&quot;,</span> <span class="pre">&quot;branch&quot;)</span></tt>.</p>
</div>
<div class="section" id="custom-renderables">
<h3>Custom Renderables<a class="headerlink" href="#custom-renderables" title="Permalink to this headline">¶</a></h3>
<p>If the options described above are not sufficient, more complex substitutions can be achieved by writing custom renderables.</p>
<p>Renderables are objects providing the <tt class="xref py py-class docutils literal"><span class="pre">IRenderable</span></tt> interface.
That interface is simple - objects must provide a <cite>getRenderingFor</cite> method.
The method should take one argument - an <tt class="xref py py-class docutils literal"><span class="pre">IProperties</span></tt> provider - and should return a string or a deferred firing with a string.
Pass instances of the class anywhere other renderables are accepted.
For example:</p>
<div class="highlight-python"><pre>class DetermineFoo(object):
    implements(IRenderable)
    def getRenderingFor(self, props)
        if props.hasProperty('bar'):
            return props['bar']
        elif props.hasProperty('baz'):
            return props['baz']
        return 'qux'
ShellCommand(command=['echo', DetermineFoo()])</pre>
</div>
<p>or, more practically,</p>
<div class="highlight-python"><pre>class Now(object):
    implements(IRenderable)
    def getRenderingFor(self, props)
        return time.clock()
ShellCommand(command=['make', Interpolate('TIME=%(kw:now)', now=Now())])</pre>
</div>
<p>This is equivalent to:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="nd">@renderer</span>
<span class="k">def</span> <span class="nf">now</span><span class="p">(</span><span class="n">props</span><span class="p">):</span>
    <span class="k">return</span> <span class="n">time</span><span class="o">.</span><span class="n">clock</span><span class="p">()</span>
<span class="n">ShellCommand</span><span class="p">(</span><span class="n">command</span><span class="o">=</span><span class="p">[</span><span class="s">&#39;make&#39;</span><span class="p">,</span> <span class="n">Interpolate</span><span class="p">(</span><span class="s">&#39;TIME=%(kw:now)&#39;</span><span class="p">,</span> <span class="n">now</span><span class="o">=</span><span class="n">now</span><span class="p">)])</span>
</pre></div>
</div>
<p>Note that a custom renderable must be instantiated (and its constructor can take whatever arguments you'd like), whereas a function decorated with <tt class="xref py py-func docutils literal"><span class="pre">renderer</span></tt> can be used directly.</p>
</div>
</div>
</div>


          </div>
        </div>
      </div>
        </div>
        <div class="sidebar">
<h3>Table Of Contents</h3>
<ul class="current">
<li class="toctree-l1"><a class="reference internal" href="../tutorial/index.html">Buildbot Tutorial</a></li>
<li class="toctree-l1 current"><a class="reference internal" href="index.html">Buildbot Manual</a><ul class="current">
<li class="toctree-l2"><a class="reference internal" href="introduction.html">Introduction</a></li>
<li class="toctree-l2"><a class="reference internal" href="installation.html">Installation</a></li>
<li class="toctree-l2"><a class="reference internal" href="concepts.html">Concepts</a></li>
<li class="toctree-l2 current"><a class="reference internal" href="configuration.html">Configuration</a><ul class="current">
<li class="toctree-l3"><a class="reference internal" href="cfg-intro.html">Configuring Buildbot</a></li>
<li class="toctree-l3"><a class="reference internal" href="cfg-global.html">Global Configuration</a></li>
<li class="toctree-l3"><a class="reference internal" href="cfg-changesources.html">Change Sources</a></li>
<li class="toctree-l3"><a class="reference internal" href="cfg-schedulers.html">Schedulers</a></li>
<li class="toctree-l3"><a class="reference internal" href="cfg-buildslaves.html">Buildslaves</a></li>
<li class="toctree-l3"><a class="reference internal" href="cfg-builders.html">Builder Configuration</a></li>
<li class="toctree-l3"><a class="reference internal" href="cfg-buildfactories.html">Build Factories</a></li>
<li class="toctree-l3 current"><a class="current reference internal" href="">Properties</a><ul class="simple">
</ul>
</li>
<li class="toctree-l3"><a class="reference internal" href="cfg-buildsteps.html">Build Steps</a></li>
<li class="toctree-l3"><a class="reference internal" href="cfg-interlocks.html">Interlocks</a></li>
<li class="toctree-l3"><a class="reference internal" href="cfg-statustargets.html">Status Targets</a></li>
</ul>
</li>
<li class="toctree-l2"><a class="reference internal" href="customization.html">Customization</a></li>
<li class="toctree-l2"><a class="reference internal" href="cmdline.html">Command-line Tool</a></li>
<li class="toctree-l2"><a class="reference internal" href="resources.html">Resources</a></li>
<li class="toctree-l2"><a class="reference internal" href="optimization.html">Optimization</a></li>
</ul>
</li>
<li class="toctree-l1"><a class="reference internal" href="../developer/index.html">Buildbot Development</a></li>
<li class="toctree-l1"><a class="reference internal" href="../relnotes/index.html">Release Notes for Buildbot v0.8.8</a></li>
</ul>

          <h3 style="margin-top: 1.5em;">Search</h3>
          <form class="search" action="../search.html" method="get">
            <input type="text" name="q" />
            <input type="submit" value="Go" />
            <input type="hidden" name="check_keywords" value="yes" />
            <input type="hidden" name="area" value="default" />
          </form>
          <p class="searchtip" style="font-size: 90%">
            Enter search terms or a module, class or function name.
          </p>
        </div>
        <div class="clearer"></div>
      </div>
    </div>

    <div class="footer-wrapper">
      <div class="footer">
        <div class="left">
          <a href="cfg-buildfactories.html" title="Build Factories"
             >previous</a> |
          <a href="cfg-buildsteps.html" title="Build Steps"
             >next</a> |
          <a href="../py-modindex.html" title="Python Module Index"
             >modules</a> |
          <a href="../genindex.html" title="General Index"
             >index</a>
            <br/>
            <a href="../_sources/manual/cfg-properties.txt"
               rel="nofollow">Show Source</a>
        </div>

        <div class="right">
          
    <div class="footer">
        &copy; Copyright Buildbot Team Members.
      Created using <a href="http://sphinx.pocoo.org/">Sphinx</a> 1.1.3.
    </div>
        </div>
        <div class="clearer"></div>
      </div>
    </div>

  </body>
</html>