|
- <!DOCTYPE html>
-
- <html lang="en" data-content_root="../">
- <head>
- <meta charset="utf-8" />
- <meta name="viewport" content="width=device-width, initial-scale=1.0" /><meta name="viewport" content="width=device-width, initial-scale=1" />
- <meta property="og:title" content="cgi — Common Gateway Interface support" />
- <meta property="og:type" content="website" />
- <meta property="og:url" content="https://docs.python.org/3/library/cgi.html" />
- <meta property="og:site_name" content="Python documentation" />
- <meta property="og:description" content="Source code: Lib/cgi.py Support module for Common Gateway Interface (CGI) scripts. This module defines a number of utilities for use by CGI scripts written in Python. The global variable maxlen can..." />
- <meta property="og:image" content="https://docs.python.org/3/_static/og-image.png" />
- <meta property="og:image:alt" content="Python documentation" />
- <meta name="description" content="Source code: Lib/cgi.py Support module for Common Gateway Interface (CGI) scripts. This module defines a number of utilities for use by CGI scripts written in Python. The global variable maxlen can..." />
- <meta property="og:image:width" content="200" />
- <meta property="og:image:height" content="200" />
- <meta name="theme-color" content="#3776ab" />
-
- <title>cgi — Common Gateway Interface support — Python 3.12.3 documentation</title><meta name="viewport" content="width=device-width, initial-scale=1.0">
-
- <link rel="stylesheet" type="text/css" href="../_static/pygments.css?v=80d5e7a1" />
- <link rel="stylesheet" type="text/css" href="../_static/pydoctheme.css?v=bb723527" />
- <link id="pygments_dark_css" media="(prefers-color-scheme: dark)" rel="stylesheet" type="text/css" href="../_static/pygments_dark.css?v=b20cc3f5" />
-
- <script src="../_static/documentation_options.js?v=2c828074"></script>
- <script src="../_static/doctools.js?v=888ff710"></script>
- <script src="../_static/sphinx_highlight.js?v=dc90522c"></script>
-
- <script src="../_static/sidebar.js"></script>
-
- <link rel="search" type="application/opensearchdescription+xml"
- title="Search within Python 3.12.3 documentation"
- href="../_static/opensearch.xml"/>
- <link rel="author" title="About these documents" href="../about.html" />
- <link rel="index" title="Index" href="../genindex.html" />
- <link rel="search" title="Search" href="../search.html" />
- <link rel="copyright" title="Copyright" href="../copyright.html" />
- <link rel="next" title="cgitb — Traceback manager for CGI scripts" href="cgitb.html" />
- <link rel="prev" title="audioop — Manipulate raw audio data" href="audioop.html" />
- <link rel="canonical" href="https://docs.python.org/3/library/cgi.html" />
-
-
-
-
-
- <style>
- @media only screen {
- table.full-width-table {
- width: 100%;
- }
- }
- </style>
- <link rel="stylesheet" href="../_static/pydoctheme_dark.css" media="(prefers-color-scheme: dark)" id="pydoctheme_dark_css">
- <link rel="shortcut icon" type="image/png" href="../_static/py.svg" />
- <script type="text/javascript" src="../_static/copybutton.js"></script>
- <script type="text/javascript" src="../_static/menu.js"></script>
- <script type="text/javascript" src="../_static/search-focus.js"></script>
- <script type="text/javascript" src="../_static/themetoggle.js"></script>
-
- </head>
- <body>
- <div class="mobile-nav">
- <input type="checkbox" id="menuToggler" class="toggler__input" aria-controls="navigation"
- aria-pressed="false" aria-expanded="false" role="button" aria-label="Menu" />
- <nav class="nav-content" role="navigation">
- <label for="menuToggler" class="toggler__label">
- <span></span>
- </label>
- <span class="nav-items-wrapper">
- <a href="https://www.python.org/" class="nav-logo">
- <img src="../_static/py.svg" alt="Python logo"/>
- </a>
- <span class="version_switcher_placeholder"></span>
- <form role="search" class="search" action="../search.html" method="get">
- <svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" class="search-icon">
- <path fill-rule="nonzero" fill="currentColor" d="M15.5 14h-.79l-.28-.27a6.5 6.5 0 001.48-5.34c-.47-2.78-2.79-5-5.59-5.34a6.505 6.505 0 00-7.27 7.27c.34 2.8 2.56 5.12 5.34 5.59a6.5 6.5 0 005.34-1.48l.27.28v.79l4.25 4.25c.41.41 1.08.41 1.49 0 .41-.41.41-1.08 0-1.49L15.5 14zm-6 0C7.01 14 5 11.99 5 9.5S7.01 5 9.5 5 14 7.01 14 9.5 11.99 14 9.5 14z"></path>
- </svg>
- <input placeholder="Quick search" aria-label="Quick search" type="search" name="q" />
- <input type="submit" value="Go"/>
- </form>
- </span>
- </nav>
- <div class="menu-wrapper">
- <nav class="menu" role="navigation" aria-label="main navigation">
- <div class="language_switcher_placeholder"></div>
-
- <label class="theme-selector-label">
- Theme
- <select class="theme-selector" oninput="activateTheme(this.value)">
- <option value="auto" selected>Auto</option>
- <option value="light">Light</option>
- <option value="dark">Dark</option>
- </select>
- </label>
- <div>
- <h3><a href="../contents.html">Table of Contents</a></h3>
- <ul>
- <li><a class="reference internal" href="#"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgi</span></code> — Common Gateway Interface support</a><ul>
- <li><a class="reference internal" href="#introduction">Introduction</a></li>
- <li><a class="reference internal" href="#using-the-cgi-module">Using the cgi module</a></li>
- <li><a class="reference internal" href="#higher-level-interface">Higher Level Interface</a></li>
- <li><a class="reference internal" href="#functions">Functions</a></li>
- <li><a class="reference internal" href="#caring-about-security">Caring about security</a></li>
- <li><a class="reference internal" href="#installing-your-cgi-script-on-a-unix-system">Installing your CGI script on a Unix system</a></li>
- <li><a class="reference internal" href="#testing-your-cgi-script">Testing your CGI script</a></li>
- <li><a class="reference internal" href="#debugging-cgi-scripts">Debugging CGI scripts</a></li>
- <li><a class="reference internal" href="#common-problems-and-solutions">Common problems and solutions</a></li>
- </ul>
- </li>
- </ul>
-
- </div>
- <div>
- <h4>Previous topic</h4>
- <p class="topless"><a href="audioop.html"
- title="previous chapter"><code class="xref py py-mod docutils literal notranslate"><span class="pre">audioop</span></code> — Manipulate raw audio data</a></p>
- </div>
- <div>
- <h4>Next topic</h4>
- <p class="topless"><a href="cgitb.html"
- title="next chapter"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgitb</span></code> — Traceback manager for CGI scripts</a></p>
- </div>
- <div role="note" aria-label="source link">
- <h3>This Page</h3>
- <ul class="this-page-menu">
- <li><a href="../bugs.html">Report a Bug</a></li>
- <li>
- <a href="https://github.com/python/cpython/blob/main/Doc/library/cgi.rst"
- rel="nofollow">Show Source
- </a>
- </li>
- </ul>
- </div>
- </nav>
- </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"
- accesskey="I">index</a></li>
- <li class="right" >
- <a href="../py-modindex.html" title="Python Module Index"
- >modules</a> |</li>
- <li class="right" >
- <a href="cgitb.html" title="cgitb — Traceback manager for CGI scripts"
- accesskey="N">next</a> |</li>
- <li class="right" >
- <a href="audioop.html" title="audioop — Manipulate raw audio data"
- accesskey="P">previous</a> |</li>
-
- <li><img src="../_static/py.svg" alt="Python logo" style="vertical-align: middle; margin-top: -1px"/></li>
- <li><a href="https://www.python.org/">Python</a> »</li>
- <li class="switchers">
- <div class="language_switcher_placeholder"></div>
- <div class="version_switcher_placeholder"></div>
- </li>
- <li>
-
- </li>
- <li id="cpython-language-and-version">
- <a href="../index.html">3.12.3 Documentation</a> »
- </li>
-
- <li class="nav-item nav-item-1"><a href="index.html" >The Python Standard Library</a> »</li>
- <li class="nav-item nav-item-2"><a href="superseded.html" accesskey="U">Superseded Modules</a> »</li>
- <li class="nav-item nav-item-this"><a href=""><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgi</span></code> — Common Gateway Interface support</a></li>
- <li class="right">
-
-
- <div class="inline-search" role="search">
- <form class="inline-search" action="../search.html" method="get">
- <input placeholder="Quick search" aria-label="Quick search" type="search" name="q" id="search-box" />
- <input type="submit" value="Go" />
- </form>
- </div>
- |
- </li>
- <li class="right">
- <label class="theme-selector-label">
- Theme
- <select class="theme-selector" oninput="activateTheme(this.value)">
- <option value="auto" selected>Auto</option>
- <option value="light">Light</option>
- <option value="dark">Dark</option>
- </select>
- </label> |</li>
-
- </ul>
- </div>
-
- <div class="document">
- <div class="documentwrapper">
- <div class="bodywrapper">
- <div class="body" role="main">
-
- <section id="module-cgi">
- <span id="cgi-common-gateway-interface-support"></span><h1><a class="reference internal" href="#module-cgi" title="cgi: Helpers for running Python scripts via the Common Gateway Interface. (deprecated)"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgi</span></code></a> — Common Gateway Interface support<a class="headerlink" href="#module-cgi" title="Link to this heading">¶</a></h1>
- <p><strong>Source code:</strong> <a class="reference external" href="https://github.com/python/cpython/tree/3.12/Lib/cgi.py">Lib/cgi.py</a></p>
- <div class="deprecated-removed" id="index-0">
- <p><span class="versionmodified">Deprecated since version 3.11, will be removed in version 3.13: </span>The <a class="reference internal" href="#module-cgi" title="cgi: Helpers for running Python scripts via the Common Gateway Interface. (deprecated)"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgi</span></code></a> module is deprecated
- (see <span class="target" id="index-1"></span><a class="pep reference external" href="https://peps.python.org/pep-0594/#cgi"><strong>PEP 594</strong></a> for details and alternatives).</p>
- <p>The <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> class can typically be replaced with
- <a class="reference internal" href="urllib.parse.html#urllib.parse.parse_qsl" title="urllib.parse.parse_qsl"><code class="xref py py-func docutils literal notranslate"><span class="pre">urllib.parse.parse_qsl()</span></code></a> for <code class="docutils literal notranslate"><span class="pre">GET</span></code> and <code class="docutils literal notranslate"><span class="pre">HEAD</span></code> requests,
- and the <a class="reference internal" href="email.message.html#module-email.message" title="email.message: The base class representing email messages."><code class="xref py py-mod docutils literal notranslate"><span class="pre">email.message</span></code></a> module or
- <a class="reference external" href="https://pypi.org/project/multipart/">multipart</a> for <code class="docutils literal notranslate"><span class="pre">POST</span></code> and <code class="docutils literal notranslate"><span class="pre">PUT</span></code>.
- Most <a class="reference internal" href="#functions-in-cgi-module"><span class="std std-ref">utility functions</span></a> have replacements.</p>
- </div>
- <hr class="docutils" />
- <p>Support module for Common Gateway Interface (CGI) scripts.</p>
- <p>This module defines a number of utilities for use by CGI scripts written in
- Python.</p>
- <p>The global variable <code class="docutils literal notranslate"><span class="pre">maxlen</span></code> can be set to an integer indicating the maximum
- size of a POST request. POST requests larger than this size will result in a
- <a class="reference internal" href="exceptions.html#ValueError" title="ValueError"><code class="xref py py-exc docutils literal notranslate"><span class="pre">ValueError</span></code></a> being raised during parsing. The default value of this
- variable is <code class="docutils literal notranslate"><span class="pre">0</span></code>, meaning the request size is unlimited.</p>
- <div class="availability docutils container">
- <p><a class="reference internal" href="intro.html#availability"><span class="std std-ref">Availability</span></a>: not Emscripten, not WASI.</p>
- <p>This module does not work or is not available on WebAssembly platforms
- <code class="docutils literal notranslate"><span class="pre">wasm32-emscripten</span></code> and <code class="docutils literal notranslate"><span class="pre">wasm32-wasi</span></code>. See
- <a class="reference internal" href="intro.html#wasm-availability"><span class="std std-ref">WebAssembly platforms</span></a> for more information.</p>
- </div>
- <section id="introduction">
- <h2>Introduction<a class="headerlink" href="#introduction" title="Link to this heading">¶</a></h2>
- <p id="cgi-intro">A CGI script is invoked by an HTTP server, usually to process user input
- submitted through an HTML <code class="docutils literal notranslate"><span class="pre"><FORM></span></code> or <code class="docutils literal notranslate"><span class="pre"><ISINDEX></span></code> element.</p>
- <p>Most often, CGI scripts live in the server’s special <code class="file docutils literal notranslate"><span class="pre">cgi-bin</span></code> directory.
- The HTTP server places all sorts of information about the request (such as the
- client’s hostname, the requested URL, the query string, and lots of other
- goodies) in the script’s shell environment, executes the script, and sends the
- script’s output back to the client.</p>
- <p>The script’s input is connected to the client too, and sometimes the form data
- is read this way; at other times the form data is passed via the “query string”
- part of the URL. This module is intended to take care of the different cases
- and provide a simpler interface to the Python script. It also provides a number
- of utilities that help in debugging scripts, and the latest addition is support
- for file uploads from a form (if your browser supports it).</p>
- <p>The output of a CGI script should consist of two sections, separated by a blank
- line. The first section contains a number of headers, telling the client what
- kind of data is following. Python code to generate a minimal header section
- looks like this:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="nb">print</span><span class="p">(</span><span class="s2">"Content-Type: text/html"</span><span class="p">)</span> <span class="c1"># HTML is following</span>
- <span class="nb">print</span><span class="p">()</span> <span class="c1"># blank line, end of headers</span>
- </pre></div>
- </div>
- <p>The second section is usually HTML, which allows the client software to display
- nicely formatted text with header, in-line images, etc. Here’s Python code that
- prints a simple piece of HTML:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="nb">print</span><span class="p">(</span><span class="s2">"<TITLE>CGI script output</TITLE>"</span><span class="p">)</span>
- <span class="nb">print</span><span class="p">(</span><span class="s2">"<H1>This is my first CGI script</H1>"</span><span class="p">)</span>
- <span class="nb">print</span><span class="p">(</span><span class="s2">"Hello, world!"</span><span class="p">)</span>
- </pre></div>
- </div>
- </section>
- <section id="using-the-cgi-module">
- <span id="id1"></span><h2>Using the cgi module<a class="headerlink" href="#using-the-cgi-module" title="Link to this heading">¶</a></h2>
- <p>Begin by writing <code class="docutils literal notranslate"><span class="pre">import</span> <span class="pre">cgi</span></code>.</p>
- <p>When you write a new script, consider adding these lines:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="kn">import</span> <span class="nn">cgitb</span>
- <span class="n">cgitb</span><span class="o">.</span><span class="n">enable</span><span class="p">()</span>
- </pre></div>
- </div>
- <p>This activates a special exception handler that will display detailed reports in
- the web browser if any errors occur. If you’d rather not show the guts of your
- program to users of your script, you can have the reports saved to files
- instead, with code like this:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="kn">import</span> <span class="nn">cgitb</span>
- <span class="n">cgitb</span><span class="o">.</span><span class="n">enable</span><span class="p">(</span><span class="n">display</span><span class="o">=</span><span class="mi">0</span><span class="p">,</span> <span class="n">logdir</span><span class="o">=</span><span class="s2">"/path/to/logdir"</span><span class="p">)</span>
- </pre></div>
- </div>
- <p>It’s very helpful to use this feature during script development. The reports
- produced by <a class="reference internal" href="cgitb.html#module-cgitb" title="cgitb: Configurable traceback handler for CGI scripts. (deprecated)"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgitb</span></code></a> provide information that can save you a lot of time in
- tracking down bugs. You can always remove the <code class="docutils literal notranslate"><span class="pre">cgitb</span></code> line later when you
- have tested your script and are confident that it works correctly.</p>
- <p>To get at submitted form data, use the <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> class. If the form
- contains non-ASCII characters, use the <em>encoding</em> keyword parameter set to the
- value of the encoding defined for the document. It is usually contained in the
- META tag in the HEAD section of the HTML document or by the
- <em class="mailheader">Content-Type</em> header. This reads the form contents from the
- standard input or the environment (depending on the value of various
- environment variables set according to the CGI standard). Since it may consume
- standard input, it should be instantiated only once.</p>
- <p>The <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> instance can be indexed like a Python dictionary.
- It allows membership testing with the <a class="reference internal" href="../reference/expressions.html#in"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">in</span></code></a> operator, and also supports
- the standard dictionary method <a class="reference internal" href="stdtypes.html#dict.keys" title="dict.keys"><code class="xref py py-meth docutils literal notranslate"><span class="pre">keys()</span></code></a> and the built-in function
- <a class="reference internal" href="functions.html#len" title="len"><code class="xref py py-func docutils literal notranslate"><span class="pre">len()</span></code></a>. Form fields containing empty strings are ignored and do not appear
- in the dictionary; to keep such values, provide a true value for the optional
- <em>keep_blank_values</em> keyword parameter when creating the <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code>
- instance.</p>
- <p>For instance, the following code (which assumes that the
- <em class="mailheader">Content-Type</em> header and blank line have already been printed)
- checks that the fields <code class="docutils literal notranslate"><span class="pre">name</span></code> and <code class="docutils literal notranslate"><span class="pre">addr</span></code> are both set to a non-empty
- string:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="n">form</span> <span class="o">=</span> <span class="n">cgi</span><span class="o">.</span><span class="n">FieldStorage</span><span class="p">()</span>
- <span class="k">if</span> <span class="s2">"name"</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">form</span> <span class="ow">or</span> <span class="s2">"addr"</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">form</span><span class="p">:</span>
- <span class="nb">print</span><span class="p">(</span><span class="s2">"<H1>Error</H1>"</span><span class="p">)</span>
- <span class="nb">print</span><span class="p">(</span><span class="s2">"Please fill in the name and addr fields."</span><span class="p">)</span>
- <span class="k">return</span>
- <span class="nb">print</span><span class="p">(</span><span class="s2">"<p>name:"</span><span class="p">,</span> <span class="n">form</span><span class="p">[</span><span class="s2">"name"</span><span class="p">]</span><span class="o">.</span><span class="n">value</span><span class="p">)</span>
- <span class="nb">print</span><span class="p">(</span><span class="s2">"<p>addr:"</span><span class="p">,</span> <span class="n">form</span><span class="p">[</span><span class="s2">"addr"</span><span class="p">]</span><span class="o">.</span><span class="n">value</span><span class="p">)</span>
- <span class="o">...</span><span class="n">further</span> <span class="n">form</span> <span class="n">processing</span> <span class="n">here</span><span class="o">...</span>
- </pre></div>
- </div>
- <p>Here the fields, accessed through <code class="docutils literal notranslate"><span class="pre">form[key]</span></code>, are themselves instances of
- <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> (or <code class="xref py py-class docutils literal notranslate"><span class="pre">MiniFieldStorage</span></code>, depending on the form
- encoding). The <code class="xref py py-attr docutils literal notranslate"><span class="pre">value</span></code> attribute of the instance yields
- the string value of the field. The <code class="xref py py-meth docutils literal notranslate"><span class="pre">getvalue()</span></code> method
- returns this string value directly; it also accepts an optional second argument
- as a default to return if the requested key is not present.</p>
- <p>If the submitted form data contains more than one field with the same name, the
- object retrieved by <code class="docutils literal notranslate"><span class="pre">form[key]</span></code> is not a <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> or
- <code class="xref py py-class docutils literal notranslate"><span class="pre">MiniFieldStorage</span></code> instance but a list of such instances. Similarly, in
- this situation, <code class="docutils literal notranslate"><span class="pre">form.getvalue(key)</span></code> would return a list of strings. If you
- expect this possibility (when your HTML form contains multiple fields with the
- same name), use the <a class="reference internal" href="#cgi.FieldStorage.getlist" title="cgi.FieldStorage.getlist"><code class="xref py py-meth docutils literal notranslate"><span class="pre">getlist()</span></code></a> method, which always returns
- a list of values (so that you do not need to special-case the single item
- case). For example, this code concatenates any number of username fields,
- separated by commas:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="n">value</span> <span class="o">=</span> <span class="n">form</span><span class="o">.</span><span class="n">getlist</span><span class="p">(</span><span class="s2">"username"</span><span class="p">)</span>
- <span class="n">usernames</span> <span class="o">=</span> <span class="s2">","</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">value</span><span class="p">)</span>
- </pre></div>
- </div>
- <p>If a field represents an uploaded file, accessing the value via the
- <code class="xref py py-attr docutils literal notranslate"><span class="pre">value</span></code> attribute or the <code class="xref py py-meth docutils literal notranslate"><span class="pre">getvalue()</span></code>
- method reads the entire file in memory as bytes. This may not be what you
- want. You can test for an uploaded file by testing either the
- <code class="xref py py-attr docutils literal notranslate"><span class="pre">filename</span></code> attribute or the <code class="xref py py-attr docutils literal notranslate"><span class="pre">file</span></code>
- attribute. You can then read the data from the <code class="xref py py-attr docutils literal notranslate"><span class="pre">file</span></code>
- attribute before it is automatically closed as part of the garbage collection of
- the <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> instance
- (the <a class="reference internal" href="io.html#io.RawIOBase.read" title="io.RawIOBase.read"><code class="xref py py-func docutils literal notranslate"><span class="pre">read()</span></code></a> and <a class="reference internal" href="io.html#io.IOBase.readline" title="io.IOBase.readline"><code class="xref py py-func docutils literal notranslate"><span class="pre">readline()</span></code></a> methods will
- return bytes):</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="n">fileitem</span> <span class="o">=</span> <span class="n">form</span><span class="p">[</span><span class="s2">"userfile"</span><span class="p">]</span>
- <span class="k">if</span> <span class="n">fileitem</span><span class="o">.</span><span class="n">file</span><span class="p">:</span>
- <span class="c1"># It's an uploaded file; count lines</span>
- <span class="n">linecount</span> <span class="o">=</span> <span class="mi">0</span>
- <span class="k">while</span> <span class="kc">True</span><span class="p">:</span>
- <span class="n">line</span> <span class="o">=</span> <span class="n">fileitem</span><span class="o">.</span><span class="n">file</span><span class="o">.</span><span class="n">readline</span><span class="p">()</span>
- <span class="k">if</span> <span class="ow">not</span> <span class="n">line</span><span class="p">:</span> <span class="k">break</span>
- <span class="n">linecount</span> <span class="o">=</span> <span class="n">linecount</span> <span class="o">+</span> <span class="mi">1</span>
- </pre></div>
- </div>
- <p><code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> objects also support being used in a <a class="reference internal" href="../reference/compound_stmts.html#with"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">with</span></code></a>
- statement, which will automatically close them when done.</p>
- <p>If an error is encountered when obtaining the contents of an uploaded file
- (for example, when the user interrupts the form submission by clicking on
- a Back or Cancel button) the <code class="xref py py-attr docutils literal notranslate"><span class="pre">done</span></code> attribute of the
- object for the field will be set to the value -1.</p>
- <p>The file upload draft standard entertains the possibility of uploading multiple
- files from one field (using a recursive <em class="mimetype">multipart/*</em> encoding).
- When this occurs, the item will be a dictionary-like <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> item.
- This can be determined by testing its <code class="xref py py-attr docutils literal notranslate"><span class="pre">type</span></code> attribute, which should be
- <em class="mimetype">multipart/form-data</em> (or perhaps another MIME type matching
- <em class="mimetype">multipart/*</em>). In this case, it can be iterated over recursively
- just like the top-level form object.</p>
- <p>When a form is submitted in the “old” format (as the query string or as a single
- data part of type <em class="mimetype">application/x-www-form-urlencoded</em>), the items will
- actually be instances of the class <code class="xref py py-class docutils literal notranslate"><span class="pre">MiniFieldStorage</span></code>. In this case, the
- <code class="xref py py-attr docutils literal notranslate"><span class="pre">list</span></code>, <code class="xref py py-attr docutils literal notranslate"><span class="pre">file</span></code>, and <code class="xref py py-attr docutils literal notranslate"><span class="pre">filename</span></code> attributes are always <code class="docutils literal notranslate"><span class="pre">None</span></code>.</p>
- <p>A form submitted via POST that also has a query string will contain both
- <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> and <code class="xref py py-class docutils literal notranslate"><span class="pre">MiniFieldStorage</span></code> items.</p>
- <div class="versionchanged">
- <p><span class="versionmodified changed">Changed in version 3.4: </span>The <code class="xref py py-attr docutils literal notranslate"><span class="pre">file</span></code> attribute is automatically closed upon the
- garbage collection of the creating <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> instance.</p>
- </div>
- <div class="versionchanged">
- <p><span class="versionmodified changed">Changed in version 3.5: </span>Added support for the context management protocol to the
- <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> class.</p>
- </div>
- </section>
- <section id="higher-level-interface">
- <h2>Higher Level Interface<a class="headerlink" href="#higher-level-interface" title="Link to this heading">¶</a></h2>
- <p>The previous section explains how to read CGI form data using the
- <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> class. This section describes a higher level interface
- which was added to this class to allow one to do it in a more readable and
- intuitive way. The interface doesn’t make the techniques described in previous
- sections obsolete — they are still useful to process file uploads efficiently,
- for example.</p>
- <p>The interface consists of two simple methods. Using the methods you can process
- form data in a generic way, without the need to worry whether only one or more
- values were posted under one name.</p>
- <p>In the previous section, you learned to write following code anytime you
- expected a user to post more than one value under one name:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="n">item</span> <span class="o">=</span> <span class="n">form</span><span class="o">.</span><span class="n">getvalue</span><span class="p">(</span><span class="s2">"item"</span><span class="p">)</span>
- <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">item</span><span class="p">,</span> <span class="nb">list</span><span class="p">):</span>
- <span class="c1"># The user is requesting more than one item.</span>
- <span class="k">else</span><span class="p">:</span>
- <span class="c1"># The user is requesting only one item.</span>
- </pre></div>
- </div>
- <p>This situation is common for example when a form contains a group of multiple
- checkboxes with the same name:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="o"><</span><span class="nb">input</span> <span class="nb">type</span><span class="o">=</span><span class="s2">"checkbox"</span> <span class="n">name</span><span class="o">=</span><span class="s2">"item"</span> <span class="n">value</span><span class="o">=</span><span class="s2">"1"</span> <span class="o">/></span>
- <span class="o"><</span><span class="nb">input</span> <span class="nb">type</span><span class="o">=</span><span class="s2">"checkbox"</span> <span class="n">name</span><span class="o">=</span><span class="s2">"item"</span> <span class="n">value</span><span class="o">=</span><span class="s2">"2"</span> <span class="o">/></span>
- </pre></div>
- </div>
- <p>In most situations, however, there’s only one form control with a particular
- name in a form and then you expect and need only one value associated with this
- name. So you write a script containing for example this code:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="n">user</span> <span class="o">=</span> <span class="n">form</span><span class="o">.</span><span class="n">getvalue</span><span class="p">(</span><span class="s2">"user"</span><span class="p">)</span><span class="o">.</span><span class="n">upper</span><span class="p">()</span>
- </pre></div>
- </div>
- <p>The problem with the code is that you should never expect that a client will
- provide valid input to your scripts. For example, if a curious user appends
- another <code class="docutils literal notranslate"><span class="pre">user=foo</span></code> pair to the query string, then the script would crash,
- because in this situation the <code class="docutils literal notranslate"><span class="pre">getvalue("user")</span></code> method call returns a list
- instead of a string. Calling the <a class="reference internal" href="stdtypes.html#str.upper" title="str.upper"><code class="xref py py-meth docutils literal notranslate"><span class="pre">upper()</span></code></a> method on a list is not valid
- (since lists do not have a method of this name) and results in an
- <a class="reference internal" href="exceptions.html#AttributeError" title="AttributeError"><code class="xref py py-exc docutils literal notranslate"><span class="pre">AttributeError</span></code></a> exception.</p>
- <p>Therefore, the appropriate way to read form data values was to always use the
- code which checks whether the obtained value is a single value or a list of
- values. That’s annoying and leads to less readable scripts.</p>
- <p>A more convenient approach is to use the methods <a class="reference internal" href="#cgi.FieldStorage.getfirst" title="cgi.FieldStorage.getfirst"><code class="xref py py-meth docutils literal notranslate"><span class="pre">getfirst()</span></code></a>
- and <a class="reference internal" href="#cgi.FieldStorage.getlist" title="cgi.FieldStorage.getlist"><code class="xref py py-meth docutils literal notranslate"><span class="pre">getlist()</span></code></a> provided by this higher level interface.</p>
- <dl class="py method">
- <dt class="sig sig-object py" id="cgi.FieldStorage.getfirst">
- <span class="sig-prename descclassname"><span class="pre">FieldStorage.</span></span><span class="sig-name descname"><span class="pre">getfirst</span></span><span class="sig-paren">(</span><em class="sig-param"><span class="n"><span class="pre">name</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">default</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">None</span></span></em><span class="sig-paren">)</span><a class="headerlink" href="#cgi.FieldStorage.getfirst" title="Link to this definition">¶</a></dt>
- <dd><p>This method always returns only one value associated with form field <em>name</em>.
- The method returns only the first value in case that more values were posted
- under such name. Please note that the order in which the values are received
- may vary from browser to browser and should not be counted on. <a class="footnote-reference brackets" href="#id3" id="id2" role="doc-noteref"><span class="fn-bracket">[</span>1<span class="fn-bracket">]</span></a> If no such
- form field or value exists then the method returns the value specified by the
- optional parameter <em>default</em>. This parameter defaults to <code class="docutils literal notranslate"><span class="pre">None</span></code> if not
- specified.</p>
- </dd></dl>
-
- <dl class="py method">
- <dt class="sig sig-object py" id="cgi.FieldStorage.getlist">
- <span class="sig-prename descclassname"><span class="pre">FieldStorage.</span></span><span class="sig-name descname"><span class="pre">getlist</span></span><span class="sig-paren">(</span><em class="sig-param"><span class="n"><span class="pre">name</span></span></em><span class="sig-paren">)</span><a class="headerlink" href="#cgi.FieldStorage.getlist" title="Link to this definition">¶</a></dt>
- <dd><p>This method always returns a list of values associated with form field <em>name</em>.
- The method returns an empty list if no such form field or value exists for
- <em>name</em>. It returns a list consisting of one item if only one such value exists.</p>
- </dd></dl>
-
- <p>Using these methods you can write nice compact code:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="kn">import</span> <span class="nn">cgi</span>
- <span class="n">form</span> <span class="o">=</span> <span class="n">cgi</span><span class="o">.</span><span class="n">FieldStorage</span><span class="p">()</span>
- <span class="n">user</span> <span class="o">=</span> <span class="n">form</span><span class="o">.</span><span class="n">getfirst</span><span class="p">(</span><span class="s2">"user"</span><span class="p">,</span> <span class="s2">""</span><span class="p">)</span><span class="o">.</span><span class="n">upper</span><span class="p">()</span> <span class="c1"># This way it's safe.</span>
- <span class="k">for</span> <span class="n">item</span> <span class="ow">in</span> <span class="n">form</span><span class="o">.</span><span class="n">getlist</span><span class="p">(</span><span class="s2">"item"</span><span class="p">):</span>
- <span class="n">do_something</span><span class="p">(</span><span class="n">item</span><span class="p">)</span>
- </pre></div>
- </div>
- </section>
- <section id="functions">
- <span id="functions-in-cgi-module"></span><h2>Functions<a class="headerlink" href="#functions" title="Link to this heading">¶</a></h2>
- <p>These are useful if you want more control, or if you want to employ some of the
- algorithms implemented in this module in other circumstances.</p>
- <dl class="py function">
- <dt class="sig sig-object py" id="cgi.parse">
- <span class="sig-prename descclassname"><span class="pre">cgi.</span></span><span class="sig-name descname"><span class="pre">parse</span></span><span class="sig-paren">(</span><em class="sig-param"><span class="n"><span class="pre">fp</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">None</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">environ</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">os.environ</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">keep_blank_values</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">False</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">strict_parsing</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">False</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">separator</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">'&'</span></span></em><span class="sig-paren">)</span><a class="headerlink" href="#cgi.parse" title="Link to this definition">¶</a></dt>
- <dd><p>Parse a query in the environment or from a file (the file defaults to
- <code class="docutils literal notranslate"><span class="pre">sys.stdin</span></code>). The <em>keep_blank_values</em>, <em>strict_parsing</em> and <em>separator</em> parameters are
- passed to <a class="reference internal" href="urllib.parse.html#urllib.parse.parse_qs" title="urllib.parse.parse_qs"><code class="xref py py-func docutils literal notranslate"><span class="pre">urllib.parse.parse_qs()</span></code></a> unchanged.</p>
- <div class="deprecated-removed">
- <p><span class="versionmodified">Deprecated since version 3.11, will be removed in version 3.13: </span>This function, like the rest of the <a class="reference internal" href="#module-cgi" title="cgi: Helpers for running Python scripts via the Common Gateway Interface. (deprecated)"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgi</span></code></a> module, is deprecated.
- It can be replaced by calling <a class="reference internal" href="urllib.parse.html#urllib.parse.parse_qs" title="urllib.parse.parse_qs"><code class="xref py py-func docutils literal notranslate"><span class="pre">urllib.parse.parse_qs()</span></code></a> directly
- on the desired query string (except for <code class="docutils literal notranslate"><span class="pre">multipart/form-data</span></code> input,
- which can be handled as described for <a class="reference internal" href="#cgi.parse_multipart" title="cgi.parse_multipart"><code class="xref py py-func docutils literal notranslate"><span class="pre">parse_multipart()</span></code></a>).</p>
- </div>
- </dd></dl>
-
- <dl class="py function">
- <dt class="sig sig-object py" id="cgi.parse_multipart">
- <span class="sig-prename descclassname"><span class="pre">cgi.</span></span><span class="sig-name descname"><span class="pre">parse_multipart</span></span><span class="sig-paren">(</span><em class="sig-param"><span class="n"><span class="pre">fp</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">pdict</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">encoding</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">'utf-8'</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">errors</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">'replace'</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">separator</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">'&'</span></span></em><span class="sig-paren">)</span><a class="headerlink" href="#cgi.parse_multipart" title="Link to this definition">¶</a></dt>
- <dd><p>Parse input of type <em class="mimetype">multipart/form-data</em> (for file uploads).
- Arguments are <em>fp</em> for the input file, <em>pdict</em> for a dictionary containing
- other parameters in the <em class="mailheader">Content-Type</em> header, and <em>encoding</em>,
- the request encoding.</p>
- <p>Returns a dictionary just like <a class="reference internal" href="urllib.parse.html#urllib.parse.parse_qs" title="urllib.parse.parse_qs"><code class="xref py py-func docutils literal notranslate"><span class="pre">urllib.parse.parse_qs()</span></code></a>: keys are the
- field names, each value is a list of values for that field. For non-file
- fields, the value is a list of strings.</p>
- <p>This is easy to use but not much good if you are expecting megabytes to be
- uploaded — in that case, use the <code class="xref py py-class docutils literal notranslate"><span class="pre">FieldStorage</span></code> class instead
- which is much more flexible.</p>
- <div class="versionchanged">
- <p><span class="versionmodified changed">Changed in version 3.7: </span>Added the <em>encoding</em> and <em>errors</em> parameters. For non-file fields, the
- value is now a list of strings, not bytes.</p>
- </div>
- <div class="versionchanged">
- <p><span class="versionmodified changed">Changed in version 3.10: </span>Added the <em>separator</em> parameter.</p>
- </div>
- <div class="deprecated-removed">
- <p><span class="versionmodified">Deprecated since version 3.11, will be removed in version 3.13: </span>This function, like the rest of the <a class="reference internal" href="#module-cgi" title="cgi: Helpers for running Python scripts via the Common Gateway Interface. (deprecated)"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgi</span></code></a> module, is deprecated.
- It can be replaced with the functionality in the <a class="reference internal" href="email.html#module-email" title="email: Package supporting the parsing, manipulating, and generating email messages."><code class="xref py py-mod docutils literal notranslate"><span class="pre">email</span></code></a> package
- (e.g. <a class="reference internal" href="email.message.html#email.message.EmailMessage" title="email.message.EmailMessage"><code class="xref py py-class docutils literal notranslate"><span class="pre">email.message.EmailMessage</span></code></a>/<a class="reference internal" href="email.compat32-message.html#email.message.Message" title="email.message.Message"><code class="xref py py-class docutils literal notranslate"><span class="pre">email.message.Message</span></code></a>)
- which implements the same MIME RFCs, or with the
- <a class="reference external" href="https://pypi.org/project/multipart/">multipart</a> PyPI project.</p>
- </div>
- </dd></dl>
-
- <dl class="py function">
- <dt class="sig sig-object py" id="cgi.parse_header">
- <span class="sig-prename descclassname"><span class="pre">cgi.</span></span><span class="sig-name descname"><span class="pre">parse_header</span></span><span class="sig-paren">(</span><em class="sig-param"><span class="n"><span class="pre">string</span></span></em><span class="sig-paren">)</span><a class="headerlink" href="#cgi.parse_header" title="Link to this definition">¶</a></dt>
- <dd><p>Parse a MIME header (such as <em class="mailheader">Content-Type</em>) into a main value and a
- dictionary of parameters.</p>
- <div class="deprecated-removed">
- <p><span class="versionmodified">Deprecated since version 3.11, will be removed in version 3.13: </span>This function, like the rest of the <a class="reference internal" href="#module-cgi" title="cgi: Helpers for running Python scripts via the Common Gateway Interface. (deprecated)"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgi</span></code></a> module, is deprecated.
- It can be replaced with the functionality in the <a class="reference internal" href="email.html#module-email" title="email: Package supporting the parsing, manipulating, and generating email messages."><code class="xref py py-mod docutils literal notranslate"><span class="pre">email</span></code></a> package,
- which implements the same MIME RFCs.</p>
- <p>For example, with <a class="reference internal" href="email.message.html#email.message.EmailMessage" title="email.message.EmailMessage"><code class="xref py py-class docutils literal notranslate"><span class="pre">email.message.EmailMessage</span></code></a>:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="kn">from</span> <span class="nn">email.message</span> <span class="kn">import</span> <span class="n">EmailMessage</span>
- <span class="n">msg</span> <span class="o">=</span> <span class="n">EmailMessage</span><span class="p">()</span>
- <span class="n">msg</span><span class="p">[</span><span class="s1">'content-type'</span><span class="p">]</span> <span class="o">=</span> <span class="s1">'application/json; charset="utf8"'</span>
- <span class="n">main</span><span class="p">,</span> <span class="n">params</span> <span class="o">=</span> <span class="n">msg</span><span class="o">.</span><span class="n">get_content_type</span><span class="p">(),</span> <span class="n">msg</span><span class="p">[</span><span class="s1">'content-type'</span><span class="p">]</span><span class="o">.</span><span class="n">params</span>
- </pre></div>
- </div>
- </div>
- </dd></dl>
-
- <dl class="py function">
- <dt class="sig sig-object py" id="cgi.test">
- <span class="sig-prename descclassname"><span class="pre">cgi.</span></span><span class="sig-name descname"><span class="pre">test</span></span><span class="sig-paren">(</span><span class="sig-paren">)</span><a class="headerlink" href="#cgi.test" title="Link to this definition">¶</a></dt>
- <dd><p>Robust test CGI script, usable as main program. Writes minimal HTTP headers and
- formats all information provided to the script in HTML format.</p>
- </dd></dl>
-
- <dl class="py function">
- <dt class="sig sig-object py" id="cgi.print_environ">
- <span class="sig-prename descclassname"><span class="pre">cgi.</span></span><span class="sig-name descname"><span class="pre">print_environ</span></span><span class="sig-paren">(</span><span class="sig-paren">)</span><a class="headerlink" href="#cgi.print_environ" title="Link to this definition">¶</a></dt>
- <dd><p>Format the shell environment in HTML.</p>
- </dd></dl>
-
- <dl class="py function">
- <dt class="sig sig-object py" id="cgi.print_form">
- <span class="sig-prename descclassname"><span class="pre">cgi.</span></span><span class="sig-name descname"><span class="pre">print_form</span></span><span class="sig-paren">(</span><em class="sig-param"><span class="n"><span class="pre">form</span></span></em><span class="sig-paren">)</span><a class="headerlink" href="#cgi.print_form" title="Link to this definition">¶</a></dt>
- <dd><p>Format a form in HTML.</p>
- </dd></dl>
-
- <dl class="py function">
- <dt class="sig sig-object py" id="cgi.print_directory">
- <span class="sig-prename descclassname"><span class="pre">cgi.</span></span><span class="sig-name descname"><span class="pre">print_directory</span></span><span class="sig-paren">(</span><span class="sig-paren">)</span><a class="headerlink" href="#cgi.print_directory" title="Link to this definition">¶</a></dt>
- <dd><p>Format the current directory in HTML.</p>
- </dd></dl>
-
- <dl class="py function">
- <dt class="sig sig-object py" id="cgi.print_environ_usage">
- <span class="sig-prename descclassname"><span class="pre">cgi.</span></span><span class="sig-name descname"><span class="pre">print_environ_usage</span></span><span class="sig-paren">(</span><span class="sig-paren">)</span><a class="headerlink" href="#cgi.print_environ_usage" title="Link to this definition">¶</a></dt>
- <dd><p>Print a list of useful (used by CGI) environment variables in HTML.</p>
- </dd></dl>
-
- </section>
- <section id="caring-about-security">
- <span id="cgi-security"></span><h2>Caring about security<a class="headerlink" href="#caring-about-security" title="Link to this heading">¶</a></h2>
- <p id="index-2">There’s one important rule: if you invoke an external program (via
- <a class="reference internal" href="os.html#os.system" title="os.system"><code class="xref py py-func docutils literal notranslate"><span class="pre">os.system()</span></code></a>, <a class="reference internal" href="os.html#os.popen" title="os.popen"><code class="xref py py-func docutils literal notranslate"><span class="pre">os.popen()</span></code></a> or other functions with similar
- functionality), make very sure you don’t pass arbitrary strings received from
- the client to the shell. This is a well-known security hole whereby clever
- hackers anywhere on the web can exploit a gullible CGI script to invoke
- arbitrary shell commands. Even parts of the URL or field names cannot be
- trusted, since the request doesn’t have to come from your form!</p>
- <p>To be on the safe side, if you must pass a string gotten from a form to a shell
- command, you should make sure the string contains only alphanumeric characters,
- dashes, underscores, and periods.</p>
- </section>
- <section id="installing-your-cgi-script-on-a-unix-system">
- <h2>Installing your CGI script on a Unix system<a class="headerlink" href="#installing-your-cgi-script-on-a-unix-system" title="Link to this heading">¶</a></h2>
- <p>Read the documentation for your HTTP server and check with your local system
- administrator to find the directory where CGI scripts should be installed;
- usually this is in a directory <code class="file docutils literal notranslate"><span class="pre">cgi-bin</span></code> in the server tree.</p>
- <p>Make sure that your script is readable and executable by “others”; the Unix file
- mode should be <code class="docutils literal notranslate"><span class="pre">0o755</span></code> octal (use <code class="docutils literal notranslate"><span class="pre">chmod</span> <span class="pre">0755</span> <span class="pre">filename</span></code>). Make sure that the
- first line of the script contains <code class="docutils literal notranslate"><span class="pre">#!</span></code> starting in column 1 followed by the
- pathname of the Python interpreter, for instance:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="ch">#!/usr/local/bin/python</span>
- </pre></div>
- </div>
- <p>Make sure the Python interpreter exists and is executable by “others”.</p>
- <p>Make sure that any files your script needs to read or write are readable or
- writable, respectively, by “others” — their mode should be <code class="docutils literal notranslate"><span class="pre">0o644</span></code> for
- readable and <code class="docutils literal notranslate"><span class="pre">0o666</span></code> for writable. This is because, for security reasons, the
- HTTP server executes your script as user “nobody”, without any special
- privileges. It can only read (write, execute) files that everybody can read
- (write, execute). The current directory at execution time is also different (it
- is usually the server’s cgi-bin directory) and the set of environment variables
- is also different from what you get when you log in. In particular, don’t count
- on the shell’s search path for executables (<span class="target" id="index-3"></span><code class="xref std std-envvar docutils literal notranslate"><span class="pre">PATH</span></code>) or the Python module
- search path (<span class="target" id="index-4"></span><a class="reference internal" href="../using/cmdline.html#envvar-PYTHONPATH"><code class="xref std std-envvar docutils literal notranslate"><span class="pre">PYTHONPATH</span></code></a>) to be set to anything interesting.</p>
- <p>If you need to load modules from a directory which is not on Python’s default
- module search path, you can change the path in your script, before importing
- other modules. For example:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="kn">import</span> <span class="nn">sys</span>
- <span class="n">sys</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">insert</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="s2">"/usr/home/joe/lib/python"</span><span class="p">)</span>
- <span class="n">sys</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">insert</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="s2">"/usr/local/lib/python"</span><span class="p">)</span>
- </pre></div>
- </div>
- <p>(This way, the directory inserted last will be searched first!)</p>
- <p>Instructions for non-Unix systems will vary; check your HTTP server’s
- documentation (it will usually have a section on CGI scripts).</p>
- </section>
- <section id="testing-your-cgi-script">
- <h2>Testing your CGI script<a class="headerlink" href="#testing-your-cgi-script" title="Link to this heading">¶</a></h2>
- <p>Unfortunately, a CGI script will generally not run when you try it from the
- command line, and a script that works perfectly from the command line may fail
- mysteriously when run from the server. There’s one reason why you should still
- test your script from the command line: if it contains a syntax error, the
- Python interpreter won’t execute it at all, and the HTTP server will most likely
- send a cryptic error to the client.</p>
- <p>Assuming your script has no syntax errors, yet it does not work, you have no
- choice but to read the next section.</p>
- </section>
- <section id="debugging-cgi-scripts">
- <h2>Debugging CGI scripts<a class="headerlink" href="#debugging-cgi-scripts" title="Link to this heading">¶</a></h2>
- <p id="index-5">First of all, check for trivial installation errors — reading the section
- above on installing your CGI script carefully can save you a lot of time. If
- you wonder whether you have understood the installation procedure correctly, try
- installing a copy of this module file (<code class="file docutils literal notranslate"><span class="pre">cgi.py</span></code>) as a CGI script. When
- invoked as a script, the file will dump its environment and the contents of the
- form in HTML format. Give it the right mode etc., and send it a request. If it’s
- installed in the standard <code class="file docutils literal notranslate"><span class="pre">cgi-bin</span></code> directory, it should be possible to
- send it a request by entering a URL into your browser of the form:</p>
- <div class="highlight-none notranslate"><div class="highlight"><pre><span></span>http://yourhostname/cgi-bin/cgi.py?name=Joe+Blow&addr=At+Home
- </pre></div>
- </div>
- <p>If this gives an error of type 404, the server cannot find the script – perhaps
- you need to install it in a different directory. If it gives another error,
- there’s an installation problem that you should fix before trying to go any
- further. If you get a nicely formatted listing of the environment and form
- content (in this example, the fields should be listed as “addr” with value “At
- Home” and “name” with value “Joe Blow”), the <code class="file docutils literal notranslate"><span class="pre">cgi.py</span></code> script has been
- installed correctly. If you follow the same procedure for your own script, you
- should now be able to debug it.</p>
- <p>The next step could be to call the <a class="reference internal" href="#module-cgi" title="cgi: Helpers for running Python scripts via the Common Gateway Interface. (deprecated)"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgi</span></code></a> module’s <a class="reference internal" href="test.html#module-test" title="test: Regression tests package containing the testing suite for Python."><code class="xref py py-func docutils literal notranslate"><span class="pre">test()</span></code></a> function
- from your script: replace its main code with the single statement</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="n">cgi</span><span class="o">.</span><span class="n">test</span><span class="p">()</span>
- </pre></div>
- </div>
- <p>This should produce the same results as those gotten from installing the
- <code class="file docutils literal notranslate"><span class="pre">cgi.py</span></code> file itself.</p>
- <p>When an ordinary Python script raises an unhandled exception (for whatever
- reason: of a typo in a module name, a file that can’t be opened, etc.), the
- Python interpreter prints a nice traceback and exits. While the Python
- interpreter will still do this when your CGI script raises an exception, most
- likely the traceback will end up in one of the HTTP server’s log files, or be
- discarded altogether.</p>
- <p>Fortunately, once you have managed to get your script to execute <em>some</em> code,
- you can easily send tracebacks to the web browser using the <a class="reference internal" href="cgitb.html#module-cgitb" title="cgitb: Configurable traceback handler for CGI scripts. (deprecated)"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgitb</span></code></a> module.
- If you haven’t done so already, just add the lines:</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="kn">import</span> <span class="nn">cgitb</span>
- <span class="n">cgitb</span><span class="o">.</span><span class="n">enable</span><span class="p">()</span>
- </pre></div>
- </div>
- <p>to the top of your script. Then try running it again; when a problem occurs,
- you should see a detailed report that will likely make apparent the cause of the
- crash.</p>
- <p>If you suspect that there may be a problem in importing the <a class="reference internal" href="cgitb.html#module-cgitb" title="cgitb: Configurable traceback handler for CGI scripts. (deprecated)"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgitb</span></code></a> module,
- you can use an even more robust approach (which only uses built-in modules):</p>
- <div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="kn">import</span> <span class="nn">sys</span>
- <span class="n">sys</span><span class="o">.</span><span class="n">stderr</span> <span class="o">=</span> <span class="n">sys</span><span class="o">.</span><span class="n">stdout</span>
- <span class="nb">print</span><span class="p">(</span><span class="s2">"Content-Type: text/plain"</span><span class="p">)</span>
- <span class="nb">print</span><span class="p">()</span>
- <span class="o">...</span><span class="n">your</span> <span class="n">code</span> <span class="n">here</span><span class="o">...</span>
- </pre></div>
- </div>
- <p>This relies on the Python interpreter to print the traceback. The content type
- of the output is set to plain text, which disables all HTML processing. If your
- script works, the raw HTML will be displayed by your client. If it raises an
- exception, most likely after the first two lines have been printed, a traceback
- will be displayed. Because no HTML interpretation is going on, the traceback
- will be readable.</p>
- </section>
- <section id="common-problems-and-solutions">
- <h2>Common problems and solutions<a class="headerlink" href="#common-problems-and-solutions" title="Link to this heading">¶</a></h2>
- <ul class="simple">
- <li><p>Most HTTP servers buffer the output from CGI scripts until the script is
- completed. This means that it is not possible to display a progress report on
- the client’s display while the script is running.</p></li>
- <li><p>Check the installation instructions above.</p></li>
- <li><p>Check the HTTP server’s log files. (<code class="docutils literal notranslate"><span class="pre">tail</span> <span class="pre">-f</span> <span class="pre">logfile</span></code> in a separate window
- may be useful!)</p></li>
- <li><p>Always check a script for syntax errors first, by doing something like
- <code class="docutils literal notranslate"><span class="pre">python</span> <span class="pre">script.py</span></code>.</p></li>
- <li><p>If your script does not have any syntax errors, try adding <code class="docutils literal notranslate"><span class="pre">import</span> <span class="pre">cgitb;</span>
- <span class="pre">cgitb.enable()</span></code> to the top of the script.</p></li>
- <li><p>When invoking external programs, make sure they can be found. Usually, this
- means using absolute path names — <span class="target" id="index-6"></span><code class="xref std std-envvar docutils literal notranslate"><span class="pre">PATH</span></code> is usually not set to a very
- useful value in a CGI script.</p></li>
- <li><p>When reading or writing external files, make sure they can be read or written
- by the userid under which your CGI script will be running: this is typically the
- userid under which the web server is running, or some explicitly specified
- userid for a web server’s <code class="docutils literal notranslate"><span class="pre">suexec</span></code> feature.</p></li>
- <li><p>Don’t try to give a CGI script a set-uid mode. This doesn’t work on most
- systems, and is a security liability as well.</p></li>
- </ul>
- <p class="rubric">Footnotes</p>
- <aside class="footnote-list brackets">
- <aside class="footnote brackets" id="id3" role="doc-footnote">
- <span class="label"><span class="fn-bracket">[</span><a role="doc-backlink" href="#id2">1</a><span class="fn-bracket">]</span></span>
- <p>Note that some recent versions of the HTML specification do state what
- order the field values should be supplied in, but knowing whether a request
- was received from a conforming browser, or even from a browser at all, is
- tedious and error-prone.</p>
- </aside>
- </aside>
- </section>
- </section>
-
-
- <div class="clearer"></div>
- </div>
- </div>
- </div>
- <div class="sphinxsidebar" role="navigation" aria-label="main navigation">
- <div class="sphinxsidebarwrapper">
- <div>
- <h3><a href="../contents.html">Table of Contents</a></h3>
- <ul>
- <li><a class="reference internal" href="#"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgi</span></code> — Common Gateway Interface support</a><ul>
- <li><a class="reference internal" href="#introduction">Introduction</a></li>
- <li><a class="reference internal" href="#using-the-cgi-module">Using the cgi module</a></li>
- <li><a class="reference internal" href="#higher-level-interface">Higher Level Interface</a></li>
- <li><a class="reference internal" href="#functions">Functions</a></li>
- <li><a class="reference internal" href="#caring-about-security">Caring about security</a></li>
- <li><a class="reference internal" href="#installing-your-cgi-script-on-a-unix-system">Installing your CGI script on a Unix system</a></li>
- <li><a class="reference internal" href="#testing-your-cgi-script">Testing your CGI script</a></li>
- <li><a class="reference internal" href="#debugging-cgi-scripts">Debugging CGI scripts</a></li>
- <li><a class="reference internal" href="#common-problems-and-solutions">Common problems and solutions</a></li>
- </ul>
- </li>
- </ul>
-
- </div>
- <div>
- <h4>Previous topic</h4>
- <p class="topless"><a href="audioop.html"
- title="previous chapter"><code class="xref py py-mod docutils literal notranslate"><span class="pre">audioop</span></code> — Manipulate raw audio data</a></p>
- </div>
- <div>
- <h4>Next topic</h4>
- <p class="topless"><a href="cgitb.html"
- title="next chapter"><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgitb</span></code> — Traceback manager for CGI scripts</a></p>
- </div>
- <div role="note" aria-label="source link">
- <h3>This Page</h3>
- <ul class="this-page-menu">
- <li><a href="../bugs.html">Report a Bug</a></li>
- <li>
- <a href="https://github.com/python/cpython/blob/main/Doc/library/cgi.rst"
- rel="nofollow">Show Source
- </a>
- </li>
- </ul>
- </div>
- </div>
- <div id="sidebarbutton" title="Collapse sidebar">
- <span>«</span>
- </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="right" >
- <a href="cgitb.html" title="cgitb — Traceback manager for CGI scripts"
- >next</a> |</li>
- <li class="right" >
- <a href="audioop.html" title="audioop — Manipulate raw audio data"
- >previous</a> |</li>
-
- <li><img src="../_static/py.svg" alt="Python logo" style="vertical-align: middle; margin-top: -1px"/></li>
- <li><a href="https://www.python.org/">Python</a> »</li>
- <li class="switchers">
- <div class="language_switcher_placeholder"></div>
- <div class="version_switcher_placeholder"></div>
- </li>
- <li>
-
- </li>
- <li id="cpython-language-and-version">
- <a href="../index.html">3.12.3 Documentation</a> »
- </li>
-
- <li class="nav-item nav-item-1"><a href="index.html" >The Python Standard Library</a> »</li>
- <li class="nav-item nav-item-2"><a href="superseded.html" >Superseded Modules</a> »</li>
- <li class="nav-item nav-item-this"><a href=""><code class="xref py py-mod docutils literal notranslate"><span class="pre">cgi</span></code> — Common Gateway Interface support</a></li>
- <li class="right">
-
-
- <div class="inline-search" role="search">
- <form class="inline-search" action="../search.html" method="get">
- <input placeholder="Quick search" aria-label="Quick search" type="search" name="q" id="search-box" />
- <input type="submit" value="Go" />
- </form>
- </div>
- |
- </li>
- <li class="right">
- <label class="theme-selector-label">
- Theme
- <select class="theme-selector" oninput="activateTheme(this.value)">
- <option value="auto" selected>Auto</option>
- <option value="light">Light</option>
- <option value="dark">Dark</option>
- </select>
- </label> |</li>
-
- </ul>
- </div>
- <div class="footer">
- ©
- <a href="../copyright.html">
-
- Copyright
-
- </a>
- 2001-2024, Python Software Foundation.
- <br />
- This page is licensed under the Python Software Foundation License Version 2.
- <br />
- Examples, recipes, and other code in the documentation are additionally licensed under the Zero Clause BSD License.
- <br />
-
- See <a href="/license.html">History and License</a> for more information.<br />
-
-
- <br />
-
- The Python Software Foundation is a non-profit corporation.
- <a href="https://www.python.org/psf/donations/">Please donate.</a>
- <br />
- <br />
- Last updated on Apr 09, 2024 (13:47 UTC).
-
- <a href="/bugs.html">Found a bug</a>?
-
- <br />
-
- Created using <a href="https://www.sphinx-doc.org/">Sphinx</a> 7.2.6.
- </div>
-
- </body>
- </html>
|