<!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>Web Status — 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="Buildbot Development" href="index.html" /> <link rel="next" title="Master-Slave API" href="master-slave.html" /> <link rel="prev" title="File Formats" href="formats.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="formats.html" title="File Formats" accesskey="P">previous</a> | <a href="master-slave.html" title="Master-Slave API" 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="web-status"> <h1>Web Status<a class="headerlink" href="#web-status" title="Permalink to this headline">¶</a></h1> <div class="section" id="jinja-web-templates"> <span id="id1"></span><h2>Jinja Web Templates<a class="headerlink" href="#jinja-web-templates" title="Permalink to this headline">¶</a></h2> <p>Buildbot uses Jinja2 to render its web interface. The authoritative source for this templating engine is <a class="reference external" href="http://jinja.pocoo.org/2/documentation/">its own documentation</a>, of course, but a few notes are in order for those who are making only minor modifications.</p> <div class="section" id="whitespace"> <h3>Whitespace<a class="headerlink" href="#whitespace" title="Permalink to this headline">¶</a></h3> <p>Jinja directives are enclosed in <tt class="docutils literal"><span class="pre">{%</span> <span class="pre">..</span> <span class="pre">%}</span></tt>, and sometimes also have dashes. These dashes strip whitespace in the output. For example:</p> <div class="highlight-none"><div class="highlight"><pre>{% for entry in entries %} <li>{{ entry }}</li> {% endfor %} </pre></div> </div> <p>will produce output with too much whitespace:</p> <div class="highlight-html"><div class="highlight"><pre><span class="nt"><li></span>pigs<span class="nt"></li></span> <span class="nt"><li></span>cows<span class="nt"></li></span> </pre></div> </div> <p>But adding the dashes will collapse that whitespace completely:</p> <div class="highlight-none"><div class="highlight"><pre>{% for entry in entries -%} <li>{{ entry }}</li> {%- endfor %} </pre></div> </div> <p>yields</p> <div class="highlight-html"><div class="highlight"><pre><span class="nt"><li></span>pigs<span class="nt"></li><li></span>cows<span class="nt"></li></span> </pre></div> </div> </div> </div> <div class="section" id="web-authorization-framework"> <span id="id2"></span><h2>Web Authorization Framework<a class="headerlink" href="#web-authorization-framework" title="Permalink to this headline">¶</a></h2> <p>Whenever any part of the web framework wants to perform some action on the buildmaster, it should check the user's authorization first.</p> <p>Always check authorization twice: once to decide whether to show the option to the user (link, button, form, whatever); and once before actually performing the action.</p> <p>To check whether to display the option, you'll usually want to pass an authz object to the Jinja template in your <tt class="xref py py-class docutils literal"><span class="pre">HtmlResource</span></tt> subclass:</p> <div class="highlight-python"><div class="highlight"><pre><span class="k">def</span> <span class="nf">content</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">req</span><span class="p">,</span> <span class="n">cxt</span><span class="p">):</span> <span class="c"># ...</span> <span class="n">cxt</span><span class="p">[</span><span class="s">'authz'</span><span class="p">]</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">getAuthz</span><span class="p">(</span><span class="n">req</span><span class="p">)</span> <span class="n">template</span> <span class="o">=</span> <span class="o">...</span> <span class="k">return</span> <span class="n">template</span><span class="o">.</span><span class="n">render</span><span class="p">(</span><span class="o">**</span><span class="n">cxt</span><span class="p">)</span> </pre></div> </div> <p>and then determine whether to advertise the action in the template:</p> <div class="highlight-none"><div class="highlight"><pre>{{ if authz.advertiseAction('myNewTrick') }} <form action="{{ myNewTrick_url }}"> ... {{ endif }} </pre></div> </div> <p>Actions can optionally require authentication, so use <tt class="docutils literal"><span class="pre">needAuthForm</span></tt> to determine whether to require a 'username' and 'passwd' field in the generated form. These fields are usually generated by <tt class="xref py py-meth docutils literal"><span class="pre">authFormIfNeeded</span></tt>:</p> <div class="highlight-none"><div class="highlight"><pre>{{ authFormIfNeeded(authz, 'myNewTrick') }} </pre></div> </div> <p>Once the POST request comes in, it's time to check authorization again. This usually looks something like</p> <div class="highlight-python"><div class="highlight"><pre><span class="n">res</span> <span class="o">=</span> <span class="k">yield</span> <span class="bp">self</span><span class="o">.</span><span class="n">getAuthz</span><span class="p">(</span><span class="n">req</span><span class="p">)</span><span class="o">.</span><span class="n">actionAllowed</span><span class="p">(</span><span class="s">'myNewTrick'</span><span class="p">,</span> <span class="n">req</span><span class="p">,</span> <span class="n">someExtraArg</span><span class="p">)</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">res</span><span class="p">:</span> <span class="n">defer</span><span class="o">.</span><span class="n">returnValue</span><span class="p">(</span><span class="n">Redirect</span><span class="p">(</span><span class="n">path_to_authfail</span><span class="p">(</span><span class="n">req</span><span class="p">)))</span> <span class="k">return</span> </pre></div> </div> <p>The <tt class="docutils literal"><span class="pre">someExtraArg</span></tt> is optional (it's handled with <tt class="docutils literal"><span class="pre">*args</span></tt>, so you can have several if you want), and is given to the user's authorization function. For example, a build-related action should pass the build status, so that the user's authorization function could ensure that devs can only operate on their own builds.</p> <p>Note that <tt class="docutils literal"><span class="pre">actionAllowed</span></tt> returns a <tt class="docutils literal"><span class="pre">Deferred</span></tt> instance, so you must wait for the <tt class="docutils literal"><span class="pre">Deferred</span></tt> and yield the <tt class="docutils literal"><span class="pre">Redirect</span></tt> instead of returning it.</p> <p>The available actions are described in <a class="reference internal" href="../manual/cfg-statustargets.html#status-WebStatus" title="WebStatus"><tt class="xref bb bb-status docutils literal"><span class="pre">WebStatus</span></tt></a>.</p> </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"><a class="reference internal" href="../manual/index.html">Buildbot Manual</a></li> <li class="toctree-l1 current"><a class="reference internal" href="index.html">Buildbot Development</a><ul class="current"> <li class="toctree-l2"><a class="reference internal" href="master-overview.html">Master Organization</a></li> <li class="toctree-l2"><a class="reference internal" href="definitions.html">Definitions</a></li> <li class="toctree-l2"><a class="reference internal" href="style.html">Buildbot Coding Style</a></li> <li class="toctree-l2"><a class="reference internal" href="tests.html">Buildbot's Test Suite</a></li> <li class="toctree-l2"><a class="reference internal" href="config.html">Configuration</a></li> <li class="toctree-l2"><a class="reference internal" href="config.html#error-handling">Error Handling</a></li> <li class="toctree-l2"><a class="reference internal" href="config.html#reconfiguration">Reconfiguration</a></li> <li class="toctree-l2"><a class="reference internal" href="utils.html">Utilities</a></li> <li class="toctree-l2"><a class="reference internal" href="database.html">Database</a></li> <li class="toctree-l2"><a class="reference internal" href="results.html">Build Result Codes</a></li> <li class="toctree-l2"><a class="reference internal" href="formats.html">File Formats</a></li> <li class="toctree-l2 current"><a class="current reference internal" href="">Web Status</a><ul class="simple"> </ul> </li> <li class="toctree-l2"><a class="reference internal" href="master-slave.html">Master-Slave API</a></li> <li class="toctree-l2"><a class="reference internal" href="encodings.html">String Encodings</a></li> <li class="toctree-l2"><a class="reference internal" href="metrics.html">Metrics</a></li> <li class="toctree-l2"><a class="reference internal" href="classes.html">Classes</a></li> </ul> </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="formats.html" title="File Formats" >previous</a> | <a href="master-slave.html" title="Master-Slave API" >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/developer/webstatus.txt" rel="nofollow">Show Source</a> </div> <div class="right"> <div class="footer"> © 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>