mirror of
https://github.com/evennia/evennia.git
synced 2026-03-18 22:06:30 +01:00
408 lines
No EOL
35 KiB
HTML
408 lines
No EOL
35 KiB
HTML
|
||
<!DOCTYPE html>
|
||
|
||
<html>
|
||
<head>
|
||
<meta charset="utf-8" />
|
||
<meta name="viewport" content="width=device-width, initial-scale=1.0" /><meta name="generator" content="Docutils 0.17.1: http://docutils.sourceforge.net/" />
|
||
|
||
<title>Debugging — Evennia 0.9.5 documentation</title>
|
||
<link rel="stylesheet" href="_static/nature.css" type="text/css" />
|
||
<link rel="stylesheet" href="_static/pygments.css" type="text/css" />
|
||
<script id="documentation_options" data-url_root="./" src="_static/documentation_options.js"></script>
|
||
<script src="_static/jquery.js"></script>
|
||
<script src="_static/underscore.js"></script>
|
||
<script src="_static/doctools.js"></script>
|
||
<script src="_static/language_data.js"></script>
|
||
<script async="async" src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.7/latest.js?config=TeX-AMS-MML_HTMLorMML"></script>
|
||
<script type="text/x-mathjax-config">MathJax.Hub.Config({"tex2jax": {"processClass": "tex2jax_process|mathjax_process|math|output_area"}})</script>
|
||
<link rel="shortcut icon" href="_static/favicon.ico"/>
|
||
<link rel="index" title="Index" href="genindex.html" />
|
||
<link rel="search" title="Search" href="search.html" />
|
||
</head><body>
|
||
<div class="related" role="navigation" aria-label="related navigation">
|
||
<h3>Navigation</h3>
|
||
<ul>
|
||
<li class="right" style="margin-right: 10px">
|
||
<a href="genindex.html" title="General Index"
|
||
accesskey="I">index</a></li>
|
||
<li class="right" >
|
||
<a href="py-modindex.html" title="Python Module Index"
|
||
>modules</a> |</li>
|
||
<li class="nav-item nav-item-0"><a href="index.html">Evennia 0.9.5</a> »</li>
|
||
<li class="nav-item nav-item-this"><a href="">Debugging</a></li>
|
||
</ul>
|
||
</div>
|
||
|
||
<div class="document">
|
||
<div class="documentwrapper">
|
||
<div class="bodywrapper">
|
||
<div class="body" role="main">
|
||
|
||
<section class="tex2jax_ignore mathjax_ignore" id="debugging">
|
||
<h1>Debugging<a class="headerlink" href="#debugging" title="Permalink to this headline">¶</a></h1>
|
||
<p>Sometimes, an error is not trivial to resolve. A few simple <code class="docutils literal notranslate"><span class="pre">print</span></code> statements is not enough to find
|
||
the cause of the issue. Running a <em>debugger</em> can then be very helpful and save a lot of time.
|
||
Debugging
|
||
means running Evennia under control of a special <em>debugger</em> program. This allows you to stop the
|
||
action at a given point, view the current state and step forward through the program to see how its
|
||
logic works.</p>
|
||
<p>Evennia natively supports these debuggers:</p>
|
||
<ul class="simple">
|
||
<li><p><a class="reference external" href="https://docs.python.org/2/library/pdb.html">Pdb</a> is a part of the Python distribution and
|
||
available out-of-the-box.</p></li>
|
||
<li><p><a class="reference external" href="https://pypi.org/project/pudb/">PuDB</a> is a third-party debugger that has a slightly more
|
||
‘graphical’, curses-based user interface than pdb. It is installed with <code class="docutils literal notranslate"><span class="pre">pip</span> <span class="pre">install</span> <span class="pre">pudb</span></code>.</p></li>
|
||
</ul>
|
||
<section id="debugging-evennia">
|
||
<h2>Debugging Evennia<a class="headerlink" href="#debugging-evennia" title="Permalink to this headline">¶</a></h2>
|
||
<p>To run Evennia with the debugger, follow these steps:</p>
|
||
<ol>
|
||
<li><p>Find the point in the code where you want to have more insight. Add the following line at that
|
||
point.</p>
|
||
<div class="highlight-python notranslate"><div class="highlight"><pre><span></span><span class="kn">from</span> <span class="nn">evennia</span> <span class="kn">import</span> <span class="n">set_trace</span><span class="p">;</span><span class="n">set_trace</span><span class="p">()</span>
|
||
</pre></div>
|
||
</div>
|
||
</li>
|
||
<li><p>(Re-)start Evennia in interactive (foreground) mode with <code class="docutils literal notranslate"><span class="pre">evennia</span> <span class="pre">istart</span></code>. This is important -
|
||
without this step the debugger will not start correctly - it will start in this interactive
|
||
terminal.</p></li>
|
||
<li><p>Perform the steps that will trigger the line where you added the <code class="docutils literal notranslate"><span class="pre">set_trace()</span></code> call. The debugger
|
||
will start in the terminal from which Evennia was interactively started.</p></li>
|
||
</ol>
|
||
<p>The <code class="docutils literal notranslate"><span class="pre">evennia.set_trace</span></code> function takes the following arguments:</p>
|
||
<div class="highlight-python notranslate"><div class="highlight"><pre><span></span> <span class="n">evennia</span><span class="o">.</span><span class="n">set_trace</span><span class="p">(</span><span class="n">debugger</span><span class="o">=</span><span class="s1">'auto'</span><span class="p">,</span> <span class="n">term_size</span><span class="o">=</span><span class="p">(</span><span class="mi">140</span><span class="p">,</span> <span class="mi">40</span><span class="p">))</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>Here, <code class="docutils literal notranslate"><span class="pre">debugger</span></code> is one of <code class="docutils literal notranslate"><span class="pre">pdb</span></code>, <code class="docutils literal notranslate"><span class="pre">pudb</span></code> or <code class="docutils literal notranslate"><span class="pre">auto</span></code>. If <code class="docutils literal notranslate"><span class="pre">auto</span></code>, use <code class="docutils literal notranslate"><span class="pre">pudb</span></code> if available, otherwise
|
||
use <code class="docutils literal notranslate"><span class="pre">pdb</span></code>. The <code class="docutils literal notranslate"><span class="pre">term_size</span></code> tuple sets the viewport size for <code class="docutils literal notranslate"><span class="pre">pudb</span></code> only (it’s ignored by <code class="docutils literal notranslate"><span class="pre">pdb</span></code>).</p>
|
||
</section>
|
||
<section id="a-simple-example-using-pdb">
|
||
<h2>A simple example using pdb<a class="headerlink" href="#a-simple-example-using-pdb" title="Permalink to this headline">¶</a></h2>
|
||
<p>The debugger is useful in different cases, but to begin with, let’s see it working in a command.
|
||
Add the following test command (which has a range of deliberate errors) and also add it to your
|
||
default cmdset. Then restart Evennia in interactive mode with <code class="docutils literal notranslate"><span class="pre">evennia</span> <span class="pre">istart</span></code>.</p>
|
||
<div class="highlight-python notranslate"><div class="highlight"><pre><span></span><span class="c1"># In file commands/command.py</span>
|
||
|
||
|
||
<span class="k">class</span> <span class="nc">CmdTest</span><span class="p">(</span><span class="n">Command</span><span class="p">):</span>
|
||
|
||
<span class="sd">"""</span>
|
||
<span class="sd"> A test command just to test pdb.</span>
|
||
|
||
<span class="sd"> Usage:</span>
|
||
<span class="sd"> test</span>
|
||
|
||
<span class="sd"> """</span>
|
||
|
||
<span class="n">key</span> <span class="o">=</span> <span class="s2">"test"</span>
|
||
|
||
<span class="k">def</span> <span class="nf">func</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
|
||
<span class="kn">from</span> <span class="nn">evennia</span> <span class="kn">import</span> <span class="n">set_trace</span><span class="p">;</span> <span class="n">set_trace</span><span class="p">()</span> <span class="c1"># <--- start of debugger</span>
|
||
<span class="n">obj</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">search</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">args</span><span class="p">)</span>
|
||
<span class="bp">self</span><span class="o">.</span><span class="n">msg</span><span class="p">(</span><span class="s2">"You've found </span><span class="si">{}</span><span class="s2">."</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">obj</span><span class="o">.</span><span class="n">get_display_name</span><span class="p">()))</span>
|
||
|
||
</pre></div>
|
||
</div>
|
||
<p>If you type <code class="docutils literal notranslate"><span class="pre">test</span></code> in your game, everything will freeze. You won’t get any feedback from the game,
|
||
and you won’t be able to enter any command (nor anyone else). It’s because the debugger has started
|
||
in your console, and you will find it here. Below is an example with <code class="docutils literal notranslate"><span class="pre">pdb</span></code>.</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="o">...</span>
|
||
<span class="o">></span> <span class="o">.../</span><span class="n">mygame</span><span class="o">/</span><span class="n">commands</span><span class="o">/</span><span class="n">command</span><span class="o">.</span><span class="n">py</span><span class="p">(</span><span class="mi">79</span><span class="p">)</span><span class="n">func</span><span class="p">()</span>
|
||
<span class="o">-></span> <span class="n">obj</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">search</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">args</span><span class="p">)</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span>
|
||
|
||
</pre></div>
|
||
</div>
|
||
<p><code class="docutils literal notranslate"><span class="pre">pdb</span></code> notes where it has stopped execution and, what line is about to be executed (in our case, <code class="docutils literal notranslate"><span class="pre">obj</span> <span class="pre">=</span> <span class="pre">self.search(self.args)</span></code>), and ask what you would like to do.</p>
|
||
<section id="listing-surrounding-lines-of-code">
|
||
<h3>Listing surrounding lines of code<a class="headerlink" href="#listing-surrounding-lines-of-code" title="Permalink to this headline">¶</a></h3>
|
||
<p>When you have the <code class="docutils literal notranslate"><span class="pre">pdb</span></code> prompt <code class="docutils literal notranslate"><span class="pre">(Pdb)</span></code>, you can type in different commands to explore the code. The
|
||
first one you should know is <code class="docutils literal notranslate"><span class="pre">list</span></code> (you can type <code class="docutils literal notranslate"><span class="pre">l</span></code> for short):</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="n">l</span>
|
||
<span class="mi">43</span>
|
||
<span class="mi">44</span> <span class="n">key</span> <span class="o">=</span> <span class="s2">"test"</span>
|
||
<span class="mi">45</span>
|
||
<span class="mi">46</span> <span class="k">def</span> <span class="nf">func</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
|
||
<span class="mi">47</span> <span class="kn">from</span> <span class="nn">evennia</span> <span class="kn">import</span> <span class="n">set_trace</span><span class="p">;</span> <span class="n">set_trace</span><span class="p">()</span> <span class="c1"># <--- start of debugger</span>
|
||
<span class="mi">48</span> <span class="o">-></span> <span class="n">obj</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">search</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">args</span><span class="p">)</span>
|
||
<span class="mi">49</span> <span class="bp">self</span><span class="o">.</span><span class="n">msg</span><span class="p">(</span><span class="s2">"You've found </span><span class="si">{}</span><span class="s2">."</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">obj</span><span class="o">.</span><span class="n">get_display_name</span><span class="p">()))</span>
|
||
<span class="mi">50</span>
|
||
<span class="mi">51</span> <span class="c1"># -------------------------------------------------------------</span>
|
||
<span class="mi">52</span> <span class="c1">#</span>
|
||
<span class="mi">53</span> <span class="c1"># The default commands inherit from</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>Okay, this didn’t do anything spectacular, but when you become more confident with <code class="docutils literal notranslate"><span class="pre">pdb</span></code> and find
|
||
yourself in lots of different files, you sometimes need to see what’s around in code. Notice that
|
||
there is a little arrow (<code class="docutils literal notranslate"><span class="pre">-></span></code>) before the line that is about to be executed.</p>
|
||
<p>This is important: <strong>about to be</strong>, not <strong>has just been</strong>. You need to tell <code class="docutils literal notranslate"><span class="pre">pdb</span></code> to go on (we’ll
|
||
soon see how).</p>
|
||
</section>
|
||
<section id="examining-variables">
|
||
<h3>Examining variables<a class="headerlink" href="#examining-variables" title="Permalink to this headline">¶</a></h3>
|
||
<p><code class="docutils literal notranslate"><span class="pre">pdb</span></code> allows you to examine variables (or really, to run any Python instruction). It is very useful
|
||
to know the values of variables at a specific line. To see a variable, just type its name (as if
|
||
you were in the Python interpreter:</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="bp">self</span>
|
||
<span class="o"><</span><span class="n">commands</span><span class="o">.</span><span class="n">command</span><span class="o">.</span><span class="n">CmdTest</span> <span class="nb">object</span> <span class="n">at</span> <span class="mh">0x045A0990</span><span class="o">></span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="bp">self</span><span class="o">.</span><span class="n">args</span>
|
||
<span class="sa">u</span><span class="s1">''</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="bp">self</span><span class="o">.</span><span class="n">caller</span>
|
||
<span class="o"><</span><span class="n">Character</span><span class="p">:</span> <span class="n">XXX</span><span class="o">></span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>If you try to see the variable <code class="docutils literal notranslate"><span class="pre">obj</span></code>, you’ll get an error:</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="n">obj</span>
|
||
<span class="o">***</span> <span class="ne">NameError</span><span class="p">:</span> <span class="n">name</span> <span class="s1">'obj'</span> <span class="ow">is</span> <span class="ow">not</span> <span class="n">defined</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>That figures, since at this point, we haven’t created the variable yet.</p>
|
||
<blockquote>
|
||
<div><p>Examining variable in this way is quite powerful. You can even run Python code and keep on
|
||
executing, which can help to check that your fix is actually working when you have identified an
|
||
error. If you have variable names that will conflict with <code class="docutils literal notranslate"><span class="pre">pdb</span></code> commands (like a <code class="docutils literal notranslate"><span class="pre">list</span></code>
|
||
variable), you can prefix your variable with <code class="docutils literal notranslate"><span class="pre">!</span></code>, to tell <code class="docutils literal notranslate"><span class="pre">pdb</span></code> that what follows is Python code.</p>
|
||
</div></blockquote>
|
||
</section>
|
||
<section id="executing-the-current-line">
|
||
<h3>Executing the current line<a class="headerlink" href="#executing-the-current-line" title="Permalink to this headline">¶</a></h3>
|
||
<p>It’s time we asked <code class="docutils literal notranslate"><span class="pre">pdb</span></code> to execute the current line. To do so, use the <code class="docutils literal notranslate"><span class="pre">next</span></code> command. You can
|
||
shorten it by just typing <code class="docutils literal notranslate"><span class="pre">n</span></code>:</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="n">n</span>
|
||
<span class="ne">AttributeError</span><span class="p">:</span> <span class="s2">"'CmdTest' object has no attribute 'search'"</span>
|
||
<span class="o">></span> <span class="o">.../</span><span class="n">mygame</span><span class="o">/</span><span class="n">commands</span><span class="o">/</span><span class="n">command</span><span class="o">.</span><span class="n">py</span><span class="p">(</span><span class="mi">79</span><span class="p">)</span><span class="n">func</span><span class="p">()</span>
|
||
<span class="o">-></span> <span class="n">obj</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">search</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">args</span><span class="p">)</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span>
|
||
</pre></div>
|
||
</div>
|
||
<p><code class="docutils literal notranslate"><span class="pre">Pdb</span></code> is complaining that you try to call the <code class="docutils literal notranslate"><span class="pre">search</span></code> method on a command… whereas there’s no
|
||
<code class="docutils literal notranslate"><span class="pre">search</span></code> method on commands. The character executing the command is in <code class="docutils literal notranslate"><span class="pre">self.caller</span></code>, so we might
|
||
change our line:</p>
|
||
<div class="highlight-python notranslate"><div class="highlight"><pre><span></span><span class="n">obj</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">caller</span><span class="o">.</span><span class="n">search</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">args</span><span class="p">)</span>
|
||
</pre></div>
|
||
</div>
|
||
</section>
|
||
<section id="letting-the-program-run">
|
||
<h3>Letting the program run<a class="headerlink" href="#letting-the-program-run" title="Permalink to this headline">¶</a></h3>
|
||
<p><code class="docutils literal notranslate"><span class="pre">pdb</span></code> is waiting to execute the same instruction… it provoked an error but it’s ready to try
|
||
again, just in case. We have fixed it in theory, but we need to reload, so we need to enter a
|
||
command. To tell <code class="docutils literal notranslate"><span class="pre">pdb</span></code> to terminate and keep on running the program, use the <code class="docutils literal notranslate"><span class="pre">continue</span></code> (or <code class="docutils literal notranslate"><span class="pre">c</span></code>)
|
||
command:</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="n">c</span>
|
||
<span class="o">...</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>You see an error being caught, that’s the error we have fixed… or hope to have. Let’s reload the
|
||
game and try again. You need to run <code class="docutils literal notranslate"><span class="pre">evennia</span> <span class="pre">istart</span></code> again and then run <code class="docutils literal notranslate"><span class="pre">test</span></code> to get into the
|
||
command again.</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="o">></span> <span class="o">.../</span><span class="n">mygame</span><span class="o">/</span><span class="n">commands</span><span class="o">/</span><span class="n">command</span><span class="o">.</span><span class="n">py</span><span class="p">(</span><span class="mi">79</span><span class="p">)</span><span class="n">func</span><span class="p">()</span>
|
||
<span class="o">-></span> <span class="n">obj</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">caller</span><span class="o">.</span><span class="n">search</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">args</span><span class="p">)</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span>
|
||
|
||
</pre></div>
|
||
</div>
|
||
<p><code class="docutils literal notranslate"><span class="pre">pdb</span></code> is about to run the line again.</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="n">n</span>
|
||
<span class="o">></span> <span class="o">.../</span><span class="n">mygame</span><span class="o">/</span><span class="n">commands</span><span class="o">/</span><span class="n">command</span><span class="o">.</span><span class="n">py</span><span class="p">(</span><span class="mi">80</span><span class="p">)</span><span class="n">func</span><span class="p">()</span>
|
||
<span class="o">-></span> <span class="bp">self</span><span class="o">.</span><span class="n">msg</span><span class="p">(</span><span class="s2">"You've found </span><span class="si">{}</span><span class="s2">."</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">obj</span><span class="o">.</span><span class="n">get_display_name</span><span class="p">()))</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>This time the line ran without error. Let’s see what is in the <code class="docutils literal notranslate"><span class="pre">obj</span></code> variable:</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="n">obj</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="nb">print</span> <span class="n">obj</span>
|
||
<span class="kc">None</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>We have entered the <code class="docutils literal notranslate"><span class="pre">test</span></code> command without parameter, so no object could be found in the search
|
||
(<code class="docutils literal notranslate"><span class="pre">self.args</span></code> is an empty string).</p>
|
||
<p>Let’s allow the command to continue and try to use an object name as parameter (although, we should
|
||
fix that bug too, it would be better):</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="n">c</span>
|
||
<span class="o">...</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>Notice that you’ll have an error in the game this time. Let’s try with a valid parameter. I have
|
||
another character, <code class="docutils literal notranslate"><span class="pre">barkeep</span></code>, in this room:</p>
|
||
<p><code class="docutils literal notranslate"><span class="pre">test</span> <span class="pre">barkeep</span></code></p>
|
||
<p>And again, the command freezes, and we have the debugger opened in the console.</p>
|
||
<p>Let’s execute this line right away:</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="o">></span> <span class="o">.../</span><span class="n">mygame</span><span class="o">/</span><span class="n">commands</span><span class="o">/</span><span class="n">command</span><span class="o">.</span><span class="n">py</span><span class="p">(</span><span class="mi">79</span><span class="p">)</span><span class="n">func</span><span class="p">()</span>
|
||
<span class="o">-></span> <span class="n">obj</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">caller</span><span class="o">.</span><span class="n">search</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">args</span><span class="p">)</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="n">n</span>
|
||
<span class="o">></span> <span class="o">.../</span><span class="n">mygame</span><span class="o">/</span><span class="n">commands</span><span class="o">/</span><span class="n">command</span><span class="o">.</span><span class="n">py</span><span class="p">(</span><span class="mi">80</span><span class="p">)</span><span class="n">func</span><span class="p">()</span>
|
||
<span class="o">-></span> <span class="bp">self</span><span class="o">.</span><span class="n">msg</span><span class="p">(</span><span class="s2">"You've found </span><span class="si">{}</span><span class="s2">."</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">obj</span><span class="o">.</span><span class="n">get_display_name</span><span class="p">()))</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="n">obj</span>
|
||
<span class="o"><</span><span class="n">Character</span><span class="p">:</span> <span class="n">barkeep</span><span class="o">></span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>At least this time we have found the object. Let’s process…</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="p">(</span><span class="n">Pdb</span><span class="p">)</span> <span class="n">n</span>
|
||
<span class="ne">TypeError</span><span class="p">:</span> <span class="s1">'get_display_name() takes exactly 2 arguments (1 given)'</span>
|
||
<span class="o">></span> <span class="o">.../</span><span class="n">mygame</span><span class="o">/</span><span class="n">commands</span><span class="o">/</span><span class="n">command</span><span class="o">.</span><span class="n">py</span><span class="p">(</span><span class="mi">80</span><span class="p">)</span><span class="n">func</span><span class="p">()</span>
|
||
<span class="o">-></span> <span class="bp">self</span><span class="o">.</span><span class="n">msg</span><span class="p">(</span><span class="s2">"You've found </span><span class="si">{}</span><span class="s2">."</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">obj</span><span class="o">.</span><span class="n">get_display_name</span><span class="p">()))</span>
|
||
<span class="p">(</span><span class="n">Pdb</span><span class="p">)</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>As an exercise, fix this error, reload and run the debugger again. Nothing better than some
|
||
experimenting!</p>
|
||
<p>Your debugging will often follow the same strategy:</p>
|
||
<ol class="simple">
|
||
<li><p>Receive an error you don’t understand.</p></li>
|
||
<li><p>Put a breaking point <strong>BEFORE</strong> the error occurs.</p></li>
|
||
<li><p>Run the code again and see the debugger open.</p></li>
|
||
<li><p>Run the program line by line,examining variables, checking the logic of instructions.</p></li>
|
||
<li><p>Continue and try again, each step a bit further toward the truth and the working feature.</p></li>
|
||
</ol>
|
||
</section>
|
||
<section id="stepping-through-a-function">
|
||
<h3>Stepping through a function<a class="headerlink" href="#stepping-through-a-function" title="Permalink to this headline">¶</a></h3>
|
||
<p><code class="docutils literal notranslate"><span class="pre">n</span></code> is useful, but it will avoid stepping inside of functions if it can. But most of the time, when
|
||
we have an error we don’t understand, it’s because we use functions or methods in a way that wasn’t
|
||
intended by the developer of the API. Perhaps using wrong arguments, or calling the function in a
|
||
situation that would cause a bug. When we have a line in the debugger that calls a function or
|
||
method, we can “step” to examine it further. For instance, in the previous example, when <code class="docutils literal notranslate"><span class="pre">pdb</span></code> was
|
||
about to execute <code class="docutils literal notranslate"><span class="pre">obj</span> <span class="pre">=</span> <span class="pre">self.caller.search(self.args)</span></code>, we may want to see what happens inside of
|
||
the <code class="docutils literal notranslate"><span class="pre">search</span></code> method.</p>
|
||
<p>To do so, use the <code class="docutils literal notranslate"><span class="pre">step</span></code> (or <code class="docutils literal notranslate"><span class="pre">s</span></code>) command. This command will show you the definition of the
|
||
function/method and you can then use <code class="docutils literal notranslate"><span class="pre">n</span></code> as before to see it line-by-line. In our little example,
|
||
stepping through a function or method isn’t that useful, but when you have an impressive set of
|
||
commands, functions and so on, it might really be handy to examine some feature and make sure they
|
||
operate as planned.</p>
|
||
</section>
|
||
</section>
|
||
<section id="cheat-sheet-of-pdb-pudb-commands">
|
||
<h2>Cheat-sheet of pdb/pudb commands<a class="headerlink" href="#cheat-sheet-of-pdb-pudb-commands" title="Permalink to this headline">¶</a></h2>
|
||
<p>PuDB and Pdb share the same commands. The only real difference is how it’s presented. The <code class="docutils literal notranslate"><span class="pre">look</span></code>
|
||
command is not needed much in <code class="docutils literal notranslate"><span class="pre">pudb</span></code> since it displays the code directly in its user interface.</p>
|
||
<table class="colwidths-auto docutils align-default">
|
||
<thead>
|
||
<tr class="row-odd"><th class="head"><p>Pdb/PuDB command</p></th>
|
||
<th class="head"><p>To do what</p></th>
|
||
</tr>
|
||
</thead>
|
||
<tbody>
|
||
<tr class="row-even"><td><p>list (or l)</p></td>
|
||
<td><p>List the lines around the point of execution (not needed for <code class="docutils literal notranslate"><span class="pre">pudb</span></code>, it will show</p></td>
|
||
</tr>
|
||
<tr class="row-odd"><td><p>this directly).</p></td>
|
||
<td><p></p></td>
|
||
</tr>
|
||
<tr class="row-even"><td><p>print (or p)</p></td>
|
||
<td><p>Display one or several variables.</p></td>
|
||
</tr>
|
||
<tr class="row-odd"><td><p><code class="docutils literal notranslate"><span class="pre">!</span></code></p></td>
|
||
<td><p>Run Python code (using a <code class="docutils literal notranslate"><span class="pre">!</span></code> is often optional).</p></td>
|
||
</tr>
|
||
<tr class="row-even"><td><p>continue (or c)</p></td>
|
||
<td><p>Continue execution and terminate the debugger for this time.</p></td>
|
||
</tr>
|
||
<tr class="row-odd"><td><p>next (or n)</p></td>
|
||
<td><p>Execute the current line and goes to the next one.</p></td>
|
||
</tr>
|
||
<tr class="row-even"><td><p>step (or s)</p></td>
|
||
<td><p>Step inside of a function or method to examine it.</p></td>
|
||
</tr>
|
||
<tr class="row-odd"><td><p><code class="docutils literal notranslate"><span class="pre"><RETURN></span></code></p></td>
|
||
<td><p>Repeat the last command (don’t type <code class="docutils literal notranslate"><span class="pre">n</span></code> repeatedly, just type it once and then press</p></td>
|
||
</tr>
|
||
<tr class="row-even"><td><p><code class="docutils literal notranslate"><span class="pre"><RETURN></span></code> to repeat it).</p></td>
|
||
<td><p></p></td>
|
||
</tr>
|
||
</tbody>
|
||
</table>
|
||
<p>If you want to learn more about debugging with Pdb, you will find an <a class="reference external" href="https://pymotw.com/3/pdb/">interesting tutorial on that
|
||
topic here</a>.</p>
|
||
</section>
|
||
</section>
|
||
|
||
|
||
<div class="clearer"></div>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
<div class="sphinxsidebar" role="navigation" aria-label="main navigation">
|
||
<div class="sphinxsidebarwrapper">
|
||
<p class="logo"><a href="index.html">
|
||
<img class="logo" src="_static/evennia_logo.png" alt="Logo"/>
|
||
</a></p>
|
||
<div id="searchbox" style="display: none" role="search">
|
||
<h3 id="searchlabel">Quick search</h3>
|
||
<div class="searchformwrapper">
|
||
<form class="search" action="search.html" method="get">
|
||
<input type="text" name="q" aria-labelledby="searchlabel" />
|
||
<input type="submit" value="Go" />
|
||
</form>
|
||
</div>
|
||
</div>
|
||
<script>$('#searchbox').show(0);</script>
|
||
<p><h3><a href="index.html">Table of Contents</a></h3>
|
||
<ul>
|
||
<li><a class="reference internal" href="#">Debugging</a><ul>
|
||
<li><a class="reference internal" href="#debugging-evennia">Debugging Evennia</a></li>
|
||
<li><a class="reference internal" href="#a-simple-example-using-pdb">A simple example using pdb</a><ul>
|
||
<li><a class="reference internal" href="#listing-surrounding-lines-of-code">Listing surrounding lines of code</a></li>
|
||
<li><a class="reference internal" href="#examining-variables">Examining variables</a></li>
|
||
<li><a class="reference internal" href="#executing-the-current-line">Executing the current line</a></li>
|
||
<li><a class="reference internal" href="#letting-the-program-run">Letting the program run</a></li>
|
||
<li><a class="reference internal" href="#stepping-through-a-function">Stepping through a function</a></li>
|
||
</ul>
|
||
</li>
|
||
<li><a class="reference internal" href="#cheat-sheet-of-pdb-pudb-commands">Cheat-sheet of pdb/pudb commands</a></li>
|
||
</ul>
|
||
</li>
|
||
</ul>
|
||
|
||
<div role="note" aria-label="source link">
|
||
<!--h3>This Page</h3-->
|
||
<ul class="this-page-menu">
|
||
<li><a href="_sources/Debugging.md.txt"
|
||
rel="nofollow">Show Page Source</a></li>
|
||
</ul>
|
||
</div><h3>Links</h3>
|
||
<ul>
|
||
<li><a href="https://www.evennia.com">Home page</a> </li>
|
||
<li><a href="https://github.com/evennia/evennia">Evennia Github</a> </li>
|
||
<li><a href="http://games.evennia.com">Game Index</a> </li>
|
||
<li><a href="http://webchat.freenode.net/?channels=evennia&uio=MT1mYWxzZSY5PXRydWUmMTE9MTk1JjEyPXRydWUbb">IRC</a> -
|
||
<a href="https://discord.gg/NecFePw">Discord</a> -
|
||
<a href="https://groups.google.com/forum/#%21forum/evennia">Forums</a>
|
||
</li>
|
||
<li><a href="http://evennia.blogspot.com/">Evennia Dev blog</a> </li>
|
||
</ul>
|
||
<h3>Versions</h3>
|
||
<ul>
|
||
<li><a href="../1.0-dev/index.html">1.0-dev (develop branch)</a></li>
|
||
<li><a href="Debugging.html">0.9.5 (v0.9.5 branch)</a></li>
|
||
</ul>
|
||
|
||
|
||
</div>
|
||
</div>
|
||
<div class="clearer"></div>
|
||
</div>
|
||
<div class="related" role="navigation" aria-label="related navigation">
|
||
<h3>Navigation</h3>
|
||
<ul>
|
||
<li class="right" style="margin-right: 10px">
|
||
<a href="genindex.html" title="General Index"
|
||
>index</a></li>
|
||
<li class="right" >
|
||
<a href="py-modindex.html" title="Python Module Index"
|
||
>modules</a> |</li>
|
||
<li class="nav-item nav-item-0"><a href="index.html">Evennia 0.9.5</a> »</li>
|
||
<li class="nav-item nav-item-this"><a href="">Debugging</a></li>
|
||
</ul>
|
||
</div>
|
||
<div class="footer" role="contentinfo">
|
||
© Copyright 2020, The Evennia developer community.
|
||
Created using <a href="https://www.sphinx-doc.org/">Sphinx</a> 3.2.1.
|
||
</div>
|
||
</body>
|
||
</html> |