<h1>Execute Python Code<aclass="headerlink"href="#execute-python-code"title="Permalink to this headline">¶</a></h1>
<p>The <codeclass="docutils literal notranslate"><spanclass="pre">@py</span></code> command supplied with the default command set of Evennia allows you to execute Python commands directly from inside the game. An alias to <codeclass="docutils literal notranslate"><spanclass="pre">@py</span></code> is simply “<codeclass="docutils literal notranslate"><spanclass="pre">!</span></code>”. <em>Access to the <codeclass="docutils literal notranslate"><spanclass="pre">@py</span></code> command should be severely restricted</em>. This is no joke - being able to execute arbitrary Python code on the server is not something you should entrust to just anybody.</p>
<h2>Available variables<aclass="headerlink"href="#available-variables"title="Permalink to this headline">¶</a></h2>
<p>A few local variables are made available when running <codeclass="docutils literal notranslate"><spanclass="pre">@py</span></code>. These offer entry into the running system.</p>
<ulclass="simple">
<li><p><strong>self</strong> / <strong>me</strong> - the calling object (i.e. you)</p></li>
<li><p><strong>here</strong> - the current caller’s location</p></li>
<li><p><strong>obj</strong> - a dummy <aclass="reference internal"href="Objects.html"><spanclass="doc">Object</span></a> instance</p></li>
<li><p><strong>evennia</strong> - Evennia’s <aclass="reference internal"href="Evennia-API.html"><spanclass="doc">flat API</span></a> - through this you can access all of Evennia.</p></li>
<p>For accessing other objects in the same room you need to use <codeclass="docutils literal notranslate"><spanclass="pre">self.search(name)</span></code>. For objects in other locations, use one of the <codeclass="docutils literal notranslate"><spanclass="pre">evennia.search_*</span></code> methods. See <aclass="reference external"href="Execute-Python-Code.html#finding-objects">below</a>.</p>
<h2>Returning output<aclass="headerlink"href="#returning-output"title="Permalink to this headline">¶</a></h2>
<p>This is an example where we import and test one of Evennia’s utilities found in <codeclass="docutils literal notranslate"><spanclass="pre">src/utils/utils.py</span></code>, but also accessible through <codeclass="docutils literal notranslate"><spanclass="pre">ev.utils</span></code>:</p>
<p>Note that we didn’t get any return value, all we where told is that the code finished executing without error. This is often the case in more complex pieces of code which has no single obvious return value. To see the output from the <codeclass="docutils literal notranslate"><spanclass="pre">time_format()</span></code> function we need to tell the system to echo it to us explicitly with <codeclass="docutils literal notranslate"><spanclass="pre">self.msg()</span></code>.</p>
<div><p>Warning: When using the <codeclass="docutils literal notranslate"><spanclass="pre">msg</span></code> function wrap our argument in <codeclass="docutils literal notranslate"><spanclass="pre">str()</span></code> to convert it into a string above. This is not strictly necessary for most types of data (Evennia will usually convert to a string behind the scenes for you). But for <em>lists</em> and <em>tuples</em> you will be confused by the output if you don’t wrap them in <codeclass="docutils literal notranslate"><spanclass="pre">str()</span></code>: only the first item of the iterable will be returned. This is because doing <codeclass="docutils literal notranslate"><spanclass="pre">msg(text)</span></code> is actually just a convenience shortcut; the full argument that <codeclass="docutils literal notranslate"><spanclass="pre">msg</span></code> accepts is something called an <em>outputfunc</em> on the form <codeclass="docutils literal notranslate"><spanclass="pre">(cmdname,</span><spanclass="pre">(args),</span><spanclass="pre">{kwargs})</span></code> (see <aclass="reference internal"href="Messagepath.html"><spanclass="doc">the message path</span></a> for more info). Sending a list/tuple confuses Evennia to think you are sending such a structure. Converting it to a string however makes it clear it should just be displayed as-is.</p>
</div></blockquote>
<p>If you were to use Python’s standard <codeclass="docutils literal notranslate"><spanclass="pre">print</span></code>, you will see the result in your current <codeclass="docutils literal notranslate"><spanclass="pre">stdout</span></code> (your terminal by default, otherwise your log file).</p>
</div>
<divclass="section"id="finding-objects">
<h2>Finding objects<aclass="headerlink"href="#finding-objects"title="Permalink to this headline">¶</a></h2>
<p>A common use for <codeclass="docutils literal notranslate"><spanclass="pre">@py</span></code> is to explore objects in the database, for debugging and performing specific operations that are not covered by a particular command.</p>
<p>Locating an object is best done using <codeclass="docutils literal notranslate"><spanclass="pre">self.search()</span></code>:</p>
<p><codeclass="docutils literal notranslate"><spanclass="pre">self.search()</span></code> is by far the most used case, but you can also search other database tables for other Evennia entities like scripts or configuration entities. To do this you can use the generic search entries found in <codeclass="docutils literal notranslate"><spanclass="pre">ev.search_*</span></code>.</p>
<p>(Note that since this becomes a simple statement, we don’t have to wrap it in <codeclass="docutils literal notranslate"><spanclass="pre">self.msg()</span></code> to get the output). You can also use the database model managers directly (accessible through the <codeclass="docutils literal notranslate"><spanclass="pre">objects</span></code> properties of database models or as <codeclass="docutils literal notranslate"><spanclass="pre">evennia.managers.*</span></code>). This is a bit more flexible since it gives you access to the full range of database search methods defined in each manager.</p>
<h2>Testing code outside the game<aclass="headerlink"href="#testing-code-outside-the-game"title="Permalink to this headline">¶</a></h2>
<p><codeclass="docutils literal notranslate"><spanclass="pre">@py</span></code> has the advantage of operating inside a running server (sharing the same process), where you can test things in real time. Much of this <em>can</em> be done from the outside too though.</p>
<p>In a terminal, cd to the top of your game directory (this bit is important since we need access to your config file) and run</p>
<p>Your default Python interpreter will start up, configured to be able to work with and import all modules of your Evennia installation. From here you can explore the database and test-run individual modules as desired.</p>
<p>It’s recommended that you get a more fully featured Python interpreter like <aclass="reference external"href="http://ipython.scipy.org/moin/">iPython</a>. If you use a virtual environment, you can just get it with <codeclass="docutils literal notranslate"><spanclass="pre">pip</span><spanclass="pre">install</span><spanclass="pre">ipython</span></code>. IPython allows you to better work over several lines, and also has a lot of other editing features, such as tab-completion and <codeclass="docutils literal notranslate"><spanclass="pre">__doc__</span></code>-string reading.</p>