uTools-Manuals/docs/python/http.server.html
2019-04-21 11:50:48 +08:00

19 lines
48 KiB
HTML
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<div class="body" role="main"><div class="section" id="module-http.server"><h1><span class="yiyi-st" id="yiyi-10">21.22. <a class="reference internal" href="#module-http.server" title="http.server: HTTP server and request handlers."><code class="xref py py-mod docutils literal"><span class="pre">http.server</span></code></a> — HTTP 服务器</span></h1><p><span class="yiyi-st" id="yiyi-11"><strong>源代码:</strong> <a class="reference external" href="https://hg.python.org/cpython/file/3.5/Lib/http/server.py">Lib / http / server.py</a></span></p><p><span class="yiyi-st" id="yiyi-12">此模块定义用于实现HTTP服务器Web服务器的类。</span></p><p><span class="yiyi-st" id="yiyi-13"><a class="reference internal" href="#http.server.HTTPServer" title="http.server.HTTPServer"><code class="xref py py-class docutils literal"><span class="pre">HTTPServer</span></code></a><a class="reference internal" href="socketserver.html#socketserver.TCPServer" title="socketserver.TCPServer"><code class="xref py py-class docutils literal"><span class="pre">socketserver.TCPServer</span></code></a> 的子类。</span><span class="yiyi-st" id="yiyi-14">它创建并监听了HTTP套接字同时提交了请求。</span><span class="yiyi-st" id="yiyi-15">用以下方式可运行一个服务器:</span></p><pre><code class="language-python"><span></span><span class="k">def</span> <span class="nf">run</span><span class="p">(</span><span class="n">server_class</span><span class="o">=</span><span class="n">HTTPServer</span><span class="p">,</span> <span class="n">handler_class</span><span class="o">=</span><span class="n">BaseHTTPRequestHandler</span><span class="p">):</span>
<span class="n">server_address</span> <span class="o">=</span> <span class="p">(</span><span class="s1">''</span><span class="p">,</span> <span class="mi">8000</span><span class="p">)</span>
<span class="n">httpd</span> <span class="o">=</span> <span class="n">server_class</span><span class="p">(</span><span class="n">server_address</span><span class="p">,</span> <span class="n">handler_class</span><span class="p">)</span>
<span class="n">httpd</span><span class="o">.</span><span class="n">serve_forever</span><span class="p">()</span>
</code></pre><dl class="class"><dt id="http.server.HTTPServer"><span class="yiyi-st" id="yiyi-16"> <em class="property">class </em><code class="descclassname">http.server.</code><code class="descname">HTTPServer</code><span class="sig-paren">(</span><em>server_address</em>, <em>RequestHandlerClass</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-17">此类通过将服务器地址存储为名为<code class="xref py py-attr docutils literal"><span class="pre">server_name</span></code><code class="xref py py-attr docutils literal"><span class="pre">server_port</span></code>的实例变量,在<a class="reference internal" href="socketserver.html#socketserver.TCPServer" title="socketserver.TCPServer"><code class="xref py py-class docutils literal"><span class="pre">TCPServer</span></code></a>类上构建。</span><span class="yiyi-st" id="yiyi-18">服务器可由处理程序访问,通常通过处理程序的<code class="xref py py-attr docutils literal"><span class="pre">服务器</span></code>实例变量。</span></p></dd></dl><p><span class="yiyi-st" id="yiyi-19">必须为<a class="reference internal" href="#http.server.HTTPServer" title="http.server.HTTPServer"><code class="xref py py-class docutils literal"><span class="pre">HTTPServer</span></code></a>提供一个<em>RequestHandlerClass</em>实例化,本模块提供三种不同的变体:</span></p><dl class="class"><dt id="http.server.BaseHTTPRequestHandler"><span class="yiyi-st" id="yiyi-20"> <em class="property">class </em><code class="descclassname">http.server.</code><code class="descname">BaseHTTPRequestHandler</code><span class="sig-paren">(</span><em>request</em>, <em>client_address</em>, <em>server</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-21">此类用于处理到达服务器的HTTP请求。</span><span class="yiyi-st" id="yiyi-22">它本身不能响应任何实际的HTTP请求它必须被子类化以处理每个请求方法例如</span><span class="yiyi-st" id="yiyi-23">GET或POST</span><span class="yiyi-st" id="yiyi-24"><a class="reference internal" href="#http.server.BaseHTTPRequestHandler" title="http.server.BaseHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">BaseHTTPRequestHandler</span></code></a>提供了许多类和实例变量,以及供子类使用的方法。</span></p><p><span class="yiyi-st" id="yiyi-25">处理程序将解析请求和头,然后调用特定于请求类型的方法。</span><span class="yiyi-st" id="yiyi-26">方法名称由请求构造。</span><span class="yiyi-st" id="yiyi-27">例如,对于请求方法<code class="docutils literal"><span class="pre">SPAM</span></code>,将调用不带参数的<code class="xref py py-meth docutils literal"><span class="pre">do_SPAM()</span></code>方法。</span><span class="yiyi-st" id="yiyi-28">所有相关信息存储在处理程序的实例变量中。</span><span class="yiyi-st" id="yiyi-29">子类不应该覆盖或扩展<a class="reference internal" href="../reference/datamodel.html#object.__init__" title="object.__init__"><code class="xref py py-meth docutils literal"><span class="pre">__init__()</span></code></a>方法。</span></p><p><span class="yiyi-st" id="yiyi-30"><a class="reference internal" href="#http.server.BaseHTTPRequestHandler" title="http.server.BaseHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">BaseHTTPRequestHandler</span></code></a>具有以下实例变量:</span></p><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.client_address"><span class="yiyi-st" id="yiyi-31"> <code class="descname">client_address</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-32">包含引用客户端地址的<code class="docutils literal"><span class="pre">(主机,</span> <span class="pre">端口)</span></code>形式的元组。</span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.server"><span class="yiyi-st" id="yiyi-33"> <code class="descname">server</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-34">包含服务器实例。</span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.close_connection"><span class="yiyi-st" id="yiyi-35"> <code class="descname">close_connection</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-36">应在<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.handle_one_request" title="http.server.BaseHTTPRequestHandler.handle_one_request"><code class="xref py py-meth docutils literal"><span class="pre">handle_one_request()</span></code></a>返回之前设置的布尔值,指示是否可能需要另一个请求,或者是否应关闭连接。</span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.requestline"><span class="yiyi-st" id="yiyi-37"> <code class="descname">requestline</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-38">包含HTTP请求行的字符串表示形式。</span><span class="yiyi-st" id="yiyi-39">终止CRLF被剥离。</span><span class="yiyi-st" id="yiyi-40">此属性应由<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.handle_one_request" title="http.server.BaseHTTPRequestHandler.handle_one_request"><code class="xref py py-meth docutils literal"><span class="pre">handle_one_request()</span></code></a>设置。</span><span class="yiyi-st" id="yiyi-41">如果没有处理有效的请求行,则应将其设置为空字符串。</span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.command"><span class="yiyi-st" id="yiyi-42"> <code class="descname">command</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-43">包含命令(请求类型)。</span><span class="yiyi-st" id="yiyi-44">例如,<code class="docutils literal"><span class="pre">'GET'</span></code></span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.path"><span class="yiyi-st" id="yiyi-45"> <code class="descname">path</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-46">包含请求路径。</span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.request_version"><span class="yiyi-st" id="yiyi-47"> <code class="descname">request_version</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-48">包含请求中的版本字符串。</span><span class="yiyi-st" id="yiyi-49">例如,<code class="docutils literal"><span class="pre">'HTTP/1.0'</span></code></span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.headers"><span class="yiyi-st" id="yiyi-50"> <code class="descname">headers</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-51">保存由<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.MessageClass" title="http.server.BaseHTTPRequestHandler.MessageClass"><code class="xref py py-attr docutils literal"><span class="pre">MessageClass</span></code></a>类变量指定的类的实例。</span><span class="yiyi-st" id="yiyi-52">本实例解析和管理HTTP请求中的头。</span><span class="yiyi-st" id="yiyi-53">来自<a class="reference internal" href="http.client.html#module-http.client" title="http.client: HTTP and HTTPS protocol client (requires sockets)."><code class="xref py py-mod docutils literal"><span class="pre">http.client</span></code></a><code class="xref py py-func docutils literal"><span class="pre">parse_headers()</span></code>函数用于解析标头并且它要求HTTP请求提供有效的<span class="target" id="index-1"></span> <a class="rfc reference external" href="https://tools.ietf.org/html/rfc2822.html"><strong>RFC 2822</strong></a>样式标题。</span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.rfile"><span class="yiyi-st" id="yiyi-54"> <code class="descname">rfile</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-55">包含一个输入流,位于可选输入数据的开头。</span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.wfile"><span class="yiyi-st" id="yiyi-56"> <code class="descname">wfile</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-57">包含用于将响应写回客户端的输出流。</span><span class="yiyi-st" id="yiyi-58">在写入此流时必须正确遵守HTTP协议。</span></p></dd></dl><p><span class="yiyi-st" id="yiyi-59"><a class="reference internal" href="#http.server.BaseHTTPRequestHandler" title="http.server.BaseHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">BaseHTTPRequestHandler</span></code></a>具有以下属性:</span></p><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.server_version"><span class="yiyi-st" id="yiyi-60"> <code class="descname">server_version</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-61">指定服务器软件版本。</span><span class="yiyi-st" id="yiyi-62">您可能想要覆盖此。</span><span class="yiyi-st" id="yiyi-63">格式是多个以空格分隔的字符串,其中每个字符串的格式名称为[/ version]。</span><span class="yiyi-st" id="yiyi-64">例如,<code class="docutils literal"><span class="pre">'BaseHTTP/0.2'</span></code></span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.sys_version"><span class="yiyi-st" id="yiyi-65"> <code class="descname">sys_version</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-66">包含可由<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.version_string" title="http.server.BaseHTTPRequestHandler.version_string"><code class="xref py py-attr docutils literal"><span class="pre">version_string</span></code></a>方法和<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.server_version" title="http.server.BaseHTTPRequestHandler.server_version"><code class="xref py py-attr docutils literal"><span class="pre">server_version</span></code></a>类变量使用的Python系统版本。</span><span class="yiyi-st" id="yiyi-67">例如,<code class="docutils literal"><span class="pre">'Python/1.4'</span></code></span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.error_message_format"><span class="yiyi-st" id="yiyi-68"> <code class="descname">error_message_format</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-69">指定由<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.send_error" title="http.server.BaseHTTPRequestHandler.send_error"><code class="xref py py-meth docutils literal"><span class="pre">send_error()</span></code></a>方法使用的格式字符串,用于为客户端构建错误响应。</span><span class="yiyi-st" id="yiyi-70">默认情况下,根据传递到<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.send_error" title="http.server.BaseHTTPRequestHandler.send_error"><code class="xref py py-meth docutils literal"><span class="pre">send_error()</span></code></a>的状态代码,从<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.responses" title="http.server.BaseHTTPRequestHandler.responses"><code class="xref py py-attr docutils literal"><span class="pre">responses</span></code></a>的变量填充字符串。</span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.error_content_type"><span class="yiyi-st" id="yiyi-71"> <code class="descname">error_content_type</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-72">指定发送到客户端的错误响应的Content-Type HTTP头。</span><span class="yiyi-st" id="yiyi-73">默认值为<code class="docutils literal"><span class="pre">'text/html'</span></code></span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.protocol_version"><span class="yiyi-st" id="yiyi-74"> <code class="descname">protocol_version</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-75">这指定在响应中使用的HTTP协议版本。</span><span class="yiyi-st" id="yiyi-76">如果设置为<code class="docutils literal"><span class="pre">'HTTP/1.1'</span></code>则服务器将允许HTTP持久连接然而您的服务器<em>必须</em>在其对客户端的所有响应中包含准确的<code class="docutils literal"><span class="pre">Content-Length</span></code>标头(使用<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.send_header" title="http.server.BaseHTTPRequestHandler.send_header"><code class="xref py py-meth docutils literal"><span class="pre">send_header()</span></code></a>)。</span><span class="yiyi-st" id="yiyi-77">为了向后兼容,该设置默认为<code class="docutils literal"><span class="pre">'HTTP/1.0'</span></code></span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.MessageClass"><span class="yiyi-st" id="yiyi-78"> <code class="descname">MessageClass</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-79">指定<a class="reference internal" href="email.message.html#email.message.Message" title="email.message.Message"><code class="xref py py-class docutils literal"><span class="pre">email.message.Message</span></code></a>类来解析HTTP标头。</span><span class="yiyi-st" id="yiyi-80">通常,这不会被覆盖,它默认为<code class="xref py py-class docutils literal"><span class="pre">http.client.HTTPMessage</span></code></span></p></dd></dl><dl class="attribute"><dt id="http.server.BaseHTTPRequestHandler.responses"><span class="yiyi-st" id="yiyi-81"> <code class="descname">responses</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-82">此属性包含错误代码整数到包含短和长消息的两元素元组的映射。</span><span class="yiyi-st" id="yiyi-83">例如,<code class="docutils literal"><span class="pre">{code</span> <span class="pre">shortmessage</span> <span class="pre">longmessage}</span></code></span><span class="yiyi-st" id="yiyi-84"><em>短消息</em>通常用作错误响应中的<em>消息</em>键,<em>longmessage</em>作为<em>说明</em>键。</span><span class="yiyi-st" id="yiyi-85">它由<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.send_response_only" title="http.server.BaseHTTPRequestHandler.send_response_only"><code class="xref py py-meth docutils literal"><span class="pre">send_response_only()</span></code></a><a class="reference internal" href="#http.server.BaseHTTPRequestHandler.send_error" title="http.server.BaseHTTPRequestHandler.send_error"><code class="xref py py-meth docutils literal"><span class="pre">send_error()</span></code></a>方法使用。</span></p></dd></dl><p><span class="yiyi-st" id="yiyi-86">A <a class="reference internal" href="#http.server.BaseHTTPRequestHandler" title="http.server.BaseHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">BaseHTTPRequestHandler</span></code></a>实例具有以下方法:</span></p><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.handle"><span class="yiyi-st" id="yiyi-87"> <code class="descname">handle</code><span class="sig-paren">(</span><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-88">调用<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.handle_one_request" title="http.server.BaseHTTPRequestHandler.handle_one_request"><code class="xref py py-meth docutils literal"><span class="pre">handle_one_request()</span></code></a>一次如果启用持久连接则多次以处理传入的HTTP请求。</span><span class="yiyi-st" id="yiyi-89">你应该永远不需要覆盖它;而是实现适当的<code class="xref py py-meth docutils literal"><span class="pre">do_*()</span></code>方法。</span></p></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.handle_one_request"><span class="yiyi-st" id="yiyi-90"> <code class="descname">handle_one_request</code><span class="sig-paren">(</span><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-91">此方法将解析并分派请求到适当的<code class="xref py py-meth docutils literal"><span class="pre">do_*()</span></code>方法。</span><span class="yiyi-st" id="yiyi-92">你应该永远不需要重写它。</span></p></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.handle_expect_100"><span class="yiyi-st" id="yiyi-93"> <code class="descname">handle_expect_100</code><span class="sig-paren">(</span><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-94">当符合HTTP / 1.1标准的服务器接收到<code class="docutils literal"><span class="pre">期望:</span> <span class="pre">100-继续</span></code>请求头时,会以<code class="docutils literal"><span class="pre">/ t4&gt; <span class="pre">继续</span></span></code>,然后按<code class="docutils literal"><span class="pre">200</span> <span class="pre">确定</span></code></span><span class="yiyi-st" id="yiyi-95">如果服务器不希望客户端继续,则可以覆盖此方法以引发错误。</span><span class="yiyi-st" id="yiyi-96">例如,</span><span class="yiyi-st" id="yiyi-97">服务器可以选择发送<code class="docutils literal"><span class="pre">417</span> <span class="pre">期望</span> <span class="pre">失败</span></code>作为响应标头和<code class="docutils literal"><span class="pre">t5&gt; <span class="pre">False</span></span></code></span></p><div class="versionadded"><p><span class="yiyi-st" id="yiyi-98"><span class="versionmodified">版本3.2中的新功能。</span></span></p></div></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.send_error"><span class="yiyi-st" id="yiyi-99"> <code class="descname">send_error</code><span class="sig-paren">(</span><em>code</em>, <em>message=None</em>, <em>explain=None</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-100">向客户端发送并记录完整的错误回复。</span><span class="yiyi-st" id="yiyi-101">数字<em>代码</em>指定HTTP错误代码其中<em>消息</em>是可选的,简短的,可读的错误描述。</span><span class="yiyi-st" id="yiyi-102"><em>explain</em>参数可用于提供有关错误的更详细信息;它将使用<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.error_message_format" title="http.server.BaseHTTPRequestHandler.error_message_format"><code class="xref py py-attr docutils literal"><span class="pre">error_message_format</span></code></a>属性格式化,并在一组完整的标题后作为响应正文发出。</span><span class="yiyi-st" id="yiyi-103"><a class="reference internal" href="#http.server.BaseHTTPRequestHandler.responses" title="http.server.BaseHTTPRequestHandler.responses"><code class="xref py py-attr docutils literal"><span class="pre">responses</span></code></a>属性保存<em>消息</em><em>说明</em>的默认值,如果未提供值,将使用该值;对于未知代码,两者的默认值是字符串<code class="docutils literal"><span class="pre">???</span></code></span><span class="yiyi-st" id="yiyi-104">如果方法为HEAD或响应代码为以下之一则正文将为空<code class="docutils literal"><span class="pre">1xx</span></code><code class="docutils literal"><span class="pre">204</span> <span class="pre"></span> <span class="pre">内容</span></code><code class="docutils literal"><span class="pre">205</span> <span class="pre">重置</span> <span class="pre">内容</span></code><code class="docutils literal"><span class="pre">304 </span> <span class="pre">不是</span> <span class="pre">修改</span></code></span></p><div class="versionchanged"><p><span class="yiyi-st" id="yiyi-105"><span class="versionmodified">在版本3.4中更改:</span>错误响应包含Content-Length标头。</span><span class="yiyi-st" id="yiyi-106">添加了<em>explain</em>参数。</span></p></div></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.send_response"><span class="yiyi-st" id="yiyi-107"> <code class="descname">send_response</code><span class="sig-paren">(</span><em>code</em>, <em>message=None</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-108">向头缓冲区添加响应头,并记录接受的请求。</span><span class="yiyi-st" id="yiyi-109">HTTP响应行写入内部缓冲区随后是<em>服务器</em><em>日期</em>标题。</span><span class="yiyi-st" id="yiyi-110">这两个头的值分别从<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.version_string" title="http.server.BaseHTTPRequestHandler.version_string"><code class="xref py py-meth docutils literal"><span class="pre">version_string()</span></code></a><a class="reference internal" href="#http.server.BaseHTTPRequestHandler.date_time_string" title="http.server.BaseHTTPRequestHandler.date_time_string"><code class="xref py py-meth docutils literal"><span class="pre">date_time_string()</span></code></a>方法中选取。</span><span class="yiyi-st" id="yiyi-111">如果服务器不打算使用<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.send_header" title="http.server.BaseHTTPRequestHandler.send_header"><code class="xref py py-meth docutils literal"><span class="pre">send_header()</span></code></a>方法发送任何其他头,则<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.send_response" title="http.server.BaseHTTPRequestHandler.send_response"><code class="xref py py-meth docutils literal"><span class="pre">send_response()</span></code></a>后应紧跟一个<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.end_headers" title="http.server.BaseHTTPRequestHandler.end_headers"><code class="xref py py-meth docutils literal"><span class="pre">end_headers()</span></code></a></span></p><div class="versionchanged"><p><span class="yiyi-st" id="yiyi-112"><span class="versionmodified">在版本3.3中更改:</span>标题存储到内部缓冲区,<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.end_headers" title="http.server.BaseHTTPRequestHandler.end_headers"><code class="xref py py-meth docutils literal"><span class="pre">end_headers()</span></code></a>需要显式调用。</span></p></div></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.send_header"><span class="yiyi-st" id="yiyi-113"> <code class="descname">send_header</code><span class="sig-paren">(</span><em>keyword</em>, <em>value</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-114">将HTTP头添加到内部缓冲区当调用<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.end_headers" title="http.server.BaseHTTPRequestHandler.end_headers"><code class="xref py py-meth docutils literal"><span class="pre">end_headers()</span></code></a><a class="reference internal" href="#http.server.BaseHTTPRequestHandler.flush_headers" title="http.server.BaseHTTPRequestHandler.flush_headers"><code class="xref py py-meth docutils literal"><span class="pre">flush_headers()</span></code></a>时,将写入输出流。</span><span class="yiyi-st" id="yiyi-115"><em>关键字</em>应指定标题关键字,<em></em>指定其值。</span><span class="yiyi-st" id="yiyi-116">注意在send_header调用完成后必须调用<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.end_headers" title="http.server.BaseHTTPRequestHandler.end_headers"><code class="xref py py-meth docutils literal"><span class="pre">end_headers()</span></code></a>才能完成操作。</span></p><div class="versionchanged"><p><span class="yiyi-st" id="yiyi-117"><span class="versionmodified">在版本3.2中更改:</span>标题存储在内部缓冲区中。</span></p></div></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.send_response_only"><span class="yiyi-st" id="yiyi-118"> <code class="descname">send_response_only</code><span class="sig-paren">(</span><em>code</em>, <em>message=None</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-119">仅发送响应头,用于在服务器向客户端发送<code class="docutils literal"><span class="pre">100</span> <span class="pre">继续</span></code>响应时的目的。</span><span class="yiyi-st" id="yiyi-120">标头未缓冲并直接发送输出流。如果未指定<em>消息</em>,则发送与响应<em>代码</em>相对应的HTTP消息。</span></p><div class="versionadded"><p><span class="yiyi-st" id="yiyi-121"><span class="versionmodified">版本3.2中的新功能。</span></span></p></div></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.end_headers"><span class="yiyi-st" id="yiyi-122"> <code class="descname">end_headers</code><span class="sig-paren">(</span><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-123">在标头缓冲区中添加一个空行表示响应中HTTP头的结尾并调用<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.flush_headers" title="http.server.BaseHTTPRequestHandler.flush_headers"><code class="xref py py-meth docutils literal"><span class="pre">flush_headers()</span></code></a></span></p><div class="versionchanged"><p><span class="yiyi-st" id="yiyi-124"><span class="versionmodified">在版本3.2中更改:</span>缓冲的标头写入输出流。</span></p></div></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.flush_headers"><span class="yiyi-st" id="yiyi-125"> <code class="descname">flush_headers</code><span class="sig-paren">(</span><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-126">最后发送头到输出流和刷新内部头缓冲区。</span></p><div class="versionadded"><p><span class="yiyi-st" id="yiyi-127"><span class="versionmodified">版本3.3中的新功能。</span></span></p></div></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.log_request"><span class="yiyi-st" id="yiyi-128"> <code class="descname">log_request</code><span class="sig-paren">(</span><em>code='-'</em>, <em>size='-'</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-129">记录接受(成功)请求。</span><span class="yiyi-st" id="yiyi-130"><em>代码</em>应指定与响应相关联的数字HTTP代码。</span><span class="yiyi-st" id="yiyi-131">如果响应的大小可用,则应将其作为<em>size</em>参数传递。</span></p></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.log_error"><span class="yiyi-st" id="yiyi-132"> <code class="descname">log_error</code><span class="sig-paren">(</span><em>...</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-133">在无法满足请求时记录错误。</span><span class="yiyi-st" id="yiyi-134">默认情况下,它将消息传递到<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.log_message" title="http.server.BaseHTTPRequestHandler.log_message"><code class="xref py py-meth docutils literal"><span class="pre">log_message()</span></code></a>,因此它采用相同的参数(<em>格式</em>和其他值)。</span></p></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.log_message"><span class="yiyi-st" id="yiyi-135"> <code class="descname">log_message</code><span class="sig-paren">(</span><em>format</em>, <em>...</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-136">将任意消息记录到<code class="docutils literal"><span class="pre">sys.stderr</span></code></span><span class="yiyi-st" id="yiyi-137">这通常被覆盖以创建自定义错误日志记录机制。</span><span class="yiyi-st" id="yiyi-138"><em>格式</em>参数是标准的printf样式格式字符串其中<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.log_message" title="http.server.BaseHTTPRequestHandler.log_message"><code class="xref py py-meth docutils literal"><span class="pre">log_message()</span></code></a>的附加参数将作为格式化的输入应用。</span><span class="yiyi-st" id="yiyi-139">客户端IP地址和当前日期和时间以每个记录的消息为前缀。</span></p></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.version_string"><span class="yiyi-st" id="yiyi-140"> <code class="descname">version_string</code><span class="sig-paren">(</span><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-141">返回服务器软件的版本字符串。</span><span class="yiyi-st" id="yiyi-142">这是<a class="reference internal" href="#http.server.BaseHTTPRequestHandler.server_version" title="http.server.BaseHTTPRequestHandler.server_version"><code class="xref py py-attr docutils literal"><span class="pre">server_version</span></code></a><a class="reference internal" href="#http.server.BaseHTTPRequestHandler.sys_version" title="http.server.BaseHTTPRequestHandler.sys_version"><code class="xref py py-attr docutils literal"><span class="pre">sys_version</span></code></a>属性的组合。</span></p></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.date_time_string"><span class="yiyi-st" id="yiyi-143"> <code class="descname">date_time_string</code><span class="sig-paren">(</span><em>timestamp=None</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-144">返回由消息头格式化的<em>timestamp</em>(必须为无或以<a class="reference internal" href="time.html#time.time" title="time.time"><code class="xref py py-func docutils literal"><span class="pre">time.time()</span></code></a>返回的格式)给出的日期和时间。</span><span class="yiyi-st" id="yiyi-145">如果省略<em>timestamp</em>,则使用当前日期和时间。</span></p><p><span class="yiyi-st" id="yiyi-146">结果如<code class="docutils literal"><span class="pre">'Sun</span> <span class="pre">06</span> <span class="pre">11月</span> <span class="pre">1994</span> <span class="pre">08:49:37 <span class="pre">GMT'</span></span></code></span></p></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.log_date_time_string"><span class="yiyi-st" id="yiyi-147"> <code class="descname">log_date_time_string</code><span class="sig-paren">(</span><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-148">返回当前日期和时间,格式为日志记录。</span></p></dd></dl><dl class="method"><dt id="http.server.BaseHTTPRequestHandler.address_string"><span class="yiyi-st" id="yiyi-149"> <code class="descname">address_string</code><span class="sig-paren">(</span><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-150">返回客户端地址。</span></p><div class="versionchanged"><p><span class="yiyi-st" id="yiyi-151"><span class="versionmodified">在版本3.3中更改:</span>以前,执行了名称查找。</span><span class="yiyi-st" id="yiyi-152">为了避免名称解析延迟它现在总是返回IP地址。</span></p></div></dd></dl></dd></dl><dl class="class"><dt id="http.server.SimpleHTTPRequestHandler"><span class="yiyi-st" id="yiyi-153"> <em class="property">class </em><code class="descclassname">http.server.</code><code class="descname">SimpleHTTPRequestHandler</code><span class="sig-paren">(</span><em>request</em>, <em>client_address</em>, <em>server</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-154">此类提供来自当前目录及其以下的文件直接将目录结构映射到HTTP请求。</span></p><p><span class="yiyi-st" id="yiyi-155">很多工作,例如解析请求,由基类<a class="reference internal" href="#http.server.BaseHTTPRequestHandler" title="http.server.BaseHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">BaseHTTPRequestHandler</span></code></a>完成。</span><span class="yiyi-st" id="yiyi-156">此类实现<a class="reference internal" href="#http.server.SimpleHTTPRequestHandler.do_GET" title="http.server.SimpleHTTPRequestHandler.do_GET"><code class="xref py py-func docutils literal"><span class="pre">do_GET()</span></code></a><a class="reference internal" href="#http.server.SimpleHTTPRequestHandler.do_HEAD" title="http.server.SimpleHTTPRequestHandler.do_HEAD"><code class="xref py py-func docutils literal"><span class="pre">do_HEAD()</span></code></a>函数。</span></p><p><span class="yiyi-st" id="yiyi-157">以下定义为<a class="reference internal" href="#http.server.SimpleHTTPRequestHandler" title="http.server.SimpleHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">SimpleHTTPRequestHandler</span></code></a>的类级属性:</span></p><dl class="attribute"><dt id="http.server.SimpleHTTPRequestHandler.server_version"><span class="yiyi-st" id="yiyi-158"> <code class="descname">server_version</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-159">这将是<code class="docutils literal"><span class="pre">“SimpleHTTP /”</span> <span class="pre">+</span> <span class="pre">__ version __</span></code>,其中<code class="docutils literal"><span class="pre">__version__</span></code>模块级。</span></p></dd></dl><dl class="attribute"><dt id="http.server.SimpleHTTPRequestHandler.extensions_map"><span class="yiyi-st" id="yiyi-160"> <code class="descname">extensions_map</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-161">将后缀映射到MIME类型的字典。</span><span class="yiyi-st" id="yiyi-162">默认值由空字符串表示,并被认为是<code class="docutils literal"><span class="pre">application/octet-stream</span></code></span><span class="yiyi-st" id="yiyi-163">映射使用不区分大小写,因此应仅包含低位密钥。</span></p></dd></dl><p><span class="yiyi-st" id="yiyi-164"><a class="reference internal" href="#http.server.SimpleHTTPRequestHandler" title="http.server.SimpleHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">SimpleHTTPRequestHandler</span></code></a>类定义以下方法:</span></p><dl class="method"><dt id="http.server.SimpleHTTPRequestHandler.do_HEAD"><span class="yiyi-st" id="yiyi-165"> <code class="descname">do_HEAD</code><span class="sig-paren">(</span><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-166">此方法服务于<code class="docutils literal"><span class="pre">'HEAD'</span></code>请求类型:它发送它将为等效的<code class="docutils literal"><span class="pre">GET</span></code>请求发送的头。</span><span class="yiyi-st" id="yiyi-167">有关可能的头的更完整的解释,请参阅<a class="reference internal" href="#http.server.SimpleHTTPRequestHandler.do_GET" title="http.server.SimpleHTTPRequestHandler.do_GET"><code class="xref py py-meth docutils literal"><span class="pre">do_GET()</span></code></a>方法。</span></p></dd></dl><dl class="method"><dt id="http.server.SimpleHTTPRequestHandler.do_GET"><span class="yiyi-st" id="yiyi-168"> <code class="descname">do_GET</code><span class="sig-paren">(</span><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-169">通过将请求解释为相对于当前工作目录的路径,将请求映射到本地文件。</span></p><p><span class="yiyi-st" id="yiyi-170">如果请求映射到目录,将检查目录中是否存在名为<code class="docutils literal"><span class="pre">index.html</span></code><code class="docutils literal"><span class="pre">index.htm</span></code>的文件(按此顺序)。</span><span class="yiyi-st" id="yiyi-171">如果找到,则返回文件的内容;否则通过调用<code class="xref py py-meth docutils literal"><span class="pre">list_directory()</span></code>方法生成目录列表。</span><span class="yiyi-st" id="yiyi-172">此方法使用<a class="reference internal" href="os.html#os.listdir" title="os.listdir"><code class="xref py py-func docutils literal"><span class="pre">os.listdir()</span></code></a>扫描目录,如果<a class="reference internal" href="os.html#os.listdir" title="os.listdir"><code class="xref py py-func docutils literal"><span class="pre">listdir()</span></code></a>失败,则会返回<code class="docutils literal"><span class="pre">404</span></code>错误响应。</span></p><p><span class="yiyi-st" id="yiyi-173">如果请求映射到文件,则会打开它并返回内容。</span><span class="yiyi-st" id="yiyi-174">任何打开请求文件的<a class="reference internal" href="exceptions.html#OSError" title="OSError"><code class="xref py py-exc docutils literal"><span class="pre">OSError</span></code></a>异常映射到<code class="docutils literal"><span class="pre">404</span></code><code class="docutils literal"><span class="pre">'文件</span> <span class="pre">,而不是</span> <span class="pre">找到'</span></code>错误。</span><span class="yiyi-st" id="yiyi-175">否则,通过调用<code class="xref py py-meth docutils literal"><span class="pre">guess_type()</span></code>方法猜测内容类型,该方法依次使用<em>extensions_map</em>变量。</span></p><p><span class="yiyi-st" id="yiyi-176">输出具有猜测的内容类型的<code class="docutils literal"><span class="pre">'Content-type:'</span></code>报头,随后是具有文件大小的<code class="docutils literal"><span class="pre">'Content-Length:'</span></code>报头和<code class="docutils literal"><span class="pre">'Last-Modified:'</span></code>头文件的修改时间。</span></p><p><span class="yiyi-st" id="yiyi-177">然后跟随一个空行,表示头的结尾,然后输出文件的内容。</span><span class="yiyi-st" id="yiyi-178">如果文件的MIME类型以<code class="docutils literal"><span class="pre">text/</span></code>开头,则文本以文本模式打开;否则使用二进制模式。</span></p><p><span class="yiyi-st" id="yiyi-179">例如,使用,请参阅<a class="reference internal" href="#module-http.server" title="http.server: HTTP server and request handlers."><code class="xref py py-mod docutils literal"><span class="pre">http.server</span></code></a>模块中<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"><span class="pre">test()</span></code></a>函数调用的实现。</span></p></dd></dl></dd></dl><p><span class="yiyi-st" id="yiyi-180"><a class="reference internal" href="#http.server.SimpleHTTPRequestHandler" title="http.server.SimpleHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">SimpleHTTPRequestHandler</span></code></a>类可以按照以下方式使用以便创建一个非常基本的web服务器来提供相对于当前目录的文件</span></p><pre><code class="language-python"><span></span><span class="kn">import</span> <span class="nn">http.server</span>
<span class="kn">import</span> <span class="nn">socketserver</span>
<span class="n">PORT</span> <span class="o">=</span> <span class="mi">8000</span>
<span class="n">Handler</span> <span class="o">=</span> <span class="n">http</span><span class="o">.</span><span class="n">server</span><span class="o">.</span><span class="n">SimpleHTTPRequestHandler</span>
<span class="n">httpd</span> <span class="o">=</span> <span class="n">socketserver</span><span class="o">.</span><span class="n">TCPServer</span><span class="p">((</span><span class="s2">""</span><span class="p">,</span> <span class="n">PORT</span><span class="p">),</span> <span class="n">Handler</span><span class="p">)</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"serving at port"</span><span class="p">,</span> <span class="n">PORT</span><span class="p">)</span>
<span class="n">httpd</span><span class="o">.</span><span class="n">serve_forever</span><span class="p">()</span>
</code></pre><p id="http-server-cli"><span class="yiyi-st" id="yiyi-181">还可以使用解释器的<a class="reference internal" href="../using/cmdline.html#cmdoption-m"><code class="xref std std-option docutils literal"><span class="pre">-m</span></code></a>开关和<code class="docutils literal"><span class="pre">端口</span><span class="pre"></span></code>t&gt;直接调用<a class="reference internal" href="#module-http.server" title="http.server: HTTP server and request handlers."><code class="xref py py-mod docutils literal"><span class="pre">http.server</span></code></a> t8&gt;参数。</span><span class="yiyi-st" id="yiyi-182">与上一个示例类似,此示例提供相对于当前目录的文件:</span></p><pre><code class="language-python"><span></span><span class="n">python</span> <span class="o">-</span><span class="n">m</span> <span class="n">http</span><span class="o">.</span><span class="n">server</span> <span class="mi">8000</span>
</code></pre><p><span class="yiyi-st" id="yiyi-183">默认情况下,服务器将自身绑定到所有接口。</span><span class="yiyi-st" id="yiyi-184">选项<code class="docutils literal"><span class="pre">-b/--bind</span></code>指定其应绑定的特定地址。</span><span class="yiyi-st" id="yiyi-185">例如以下命令使服务器仅绑定到localhost</span></p><pre><code class="language-python"><span></span><span class="n">python</span> <span class="o">-</span><span class="n">m</span> <span class="n">http</span><span class="o">.</span><span class="n">server</span> <span class="mi">8000</span> <span class="o">--</span><span class="n">bind</span> <span class="mf">127.0</span><span class="o">.</span><span class="mf">0.1</span>
</code></pre><div class="versionadded"><p><span class="yiyi-st" id="yiyi-186"><span class="versionmodified">版本3.4中新增:</span> <code class="docutils literal"><span class="pre">--bind</span></code>参数。</span></p></div><dl class="class"><dt id="http.server.CGIHTTPRequestHandler"><span class="yiyi-st" id="yiyi-187"> <em class="property">class </em><code class="descclassname">http.server.</code><code class="descname">CGIHTTPRequestHandler</code><span class="sig-paren">(</span><em>request</em>, <em>client_address</em>, <em>server</em><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-188">这个类用于从当前目录和下面的文件或CGI脚本的输出。</span><span class="yiyi-st" id="yiyi-189">请注意将HTTP层次结构映射到本地目录结构与在<a class="reference internal" href="#http.server.SimpleHTTPRequestHandler" title="http.server.SimpleHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">SimpleHTTPRequestHandler</span></code></a>中的完全一样。</span></p><div class="admonition note"><p class="first admonition-title"><span class="yiyi-st" id="yiyi-190">注意</span></p><p class="last"><span class="yiyi-st" id="yiyi-191">由于在执行CGI脚本之前发送代码200随后的脚本输出<a class="reference internal" href="#http.server.CGIHTTPRequestHandler" title="http.server.CGIHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">CGIHTTPRequestHandler</span></code></a>类运行的CGI脚本不能执行重定向HTTP代码302</span><span class="yiyi-st" id="yiyi-192">这将抢占状态代码。</span></p></div><p><span class="yiyi-st" id="yiyi-193">然而类将运行CGI脚本而不是将其作为文件如果它猜测它是一个CGI脚本。</span><span class="yiyi-st" id="yiyi-194">仅使用基于目录的CGI - 其他常见的服务器配置是将特殊扩展视为表示CGI脚本。</span></p><p><span class="yiyi-st" id="yiyi-195">修改<code class="xref py py-func docutils literal"><span class="pre">do_GET()</span></code><code class="xref py py-func docutils literal"><span class="pre">do_HEAD()</span></code>函数以运行CGI脚本并提供输出而不是提供文件如果请求导向<code class="docutils literal"><span class="pre">cgi_directories</span></code>路径。</span></p><p><span class="yiyi-st" id="yiyi-196"><a class="reference internal" href="#http.server.CGIHTTPRequestHandler" title="http.server.CGIHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">CGIHTTPRequestHandler</span></code></a>定义以下数据成员:</span></p><dl class="attribute"><dt id="http.server.CGIHTTPRequestHandler.cgi_directories"><span class="yiyi-st" id="yiyi-197"> <code class="descname">cgi_directories</code></span></dt><dd><p><span class="yiyi-st" id="yiyi-198">这默认为<code class="docutils literal"><span class="pre">['/ cgi-bin'</span> <span class="pre">'/ htbin']</span></code>并描述要作为包含CGI脚本的目录。</span></p></dd></dl><p><span class="yiyi-st" id="yiyi-199"><a class="reference internal" href="#http.server.CGIHTTPRequestHandler" title="http.server.CGIHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">CGIHTTPRequestHandler</span></code></a>定义以下方法:</span></p><dl class="method"><dt id="http.server.CGIHTTPRequestHandler.do_POST"><span class="yiyi-st" id="yiyi-200"> <code class="descname">do_POST</code><span class="sig-paren">(</span><span class="sig-paren">)</span></span></dt><dd><p><span class="yiyi-st" id="yiyi-201">此方法提供<code class="docutils literal"><span class="pre">'POST'</span></code>请求类型仅适用于CGI脚本。</span><span class="yiyi-st" id="yiyi-202">错误501“只能发送到CGI脚本”当尝试POST到非CGI URL时输出。</span></p></dd></dl><p><span class="yiyi-st" id="yiyi-203">注意出于安全原因CGI脚本将以用户nobody的UID运行。</span><span class="yiyi-st" id="yiyi-204">CGI脚本的问题将被转换为错误403。</span></p></dd></dl><p><span class="yiyi-st" id="yiyi-205">可以通过传递<code class="docutils literal"><span class="pre">--cgi</span></code>选项在命令行中启用<a class="reference internal" href="#http.server.CGIHTTPRequestHandler" title="http.server.CGIHTTPRequestHandler"><code class="xref py py-class docutils literal"><span class="pre">CGIHTTPRequestHandler</span></code></a></span></p><pre><code class="language-python"><span></span><span class="n">python</span> <span class="o">-</span><span class="n">m</span> <span class="n">http</span><span class="o">.</span><span class="n">server</span> <span class="o">--</span><span class="n">cgi</span> <span class="mi">8000</span>
</code></pre></div></div>