mirror of
https://github.com/evennia/evennia.git
synced 2026-03-20 06:46:31 +01:00
477 lines
No EOL
54 KiB
HTML
477 lines
No EOL
54 KiB
HTML
|
|
<!DOCTYPE html>
|
|
|
|
<html lang="en">
|
|
<head>
|
|
<meta charset="utf-8" />
|
|
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
|
<title>django.utils.http — Evennia latest documentation</title>
|
|
<link rel="stylesheet" href="../../../_static/nature.css" type="text/css" />
|
|
<link rel="stylesheet" href="../../../_static/pygments.css" type="text/css" />
|
|
<link rel="stylesheet" type="text/css" href="../../../_static/pygments.css?v=d75fae25" />
|
|
<link rel="stylesheet" type="text/css" href="../../../_static/nature.css?v=245aff17" />
|
|
<script id="documentation_options" data-url_root="../../../" src="../../../_static/documentation_options.js"></script>
|
|
<script src="../../../_static/documentation_options.js?v=c6e86fd7"></script>
|
|
<script src="../../../_static/doctools.js?v=9bcbadda"></script>
|
|
<script src="../../../_static/sphinx_highlight.js?v=dc90522c"></script>
|
|
<link rel="index" title="Index" href="../../../genindex.html" />
|
|
<link rel="search" title="Search" href="../../../search.html" />
|
|
</head><body>
|
|
|
|
|
|
|
|
|
|
<div class="related" role="navigation" aria-label="related navigation">
|
|
<h3>Navigation</h3>
|
|
<ul>
|
|
<li class="right" style="margin-right: 10px">
|
|
<a href="../../../genindex.html" title="General Index"
|
|
accesskey="I">index</a></li>
|
|
<li class="right" >
|
|
<a href="../../../py-modindex.html" title="Python Module Index"
|
|
>modules</a> |</li>
|
|
<li class="nav-item nav-item-0"><a href="../../../index.html">Evennia latest</a> »</li>
|
|
<li class="nav-item nav-item-1"><a href="../../index.html" accesskey="U">Module code</a> »</li>
|
|
<li class="nav-item nav-item-this"><a href="">django.utils.http</a></li>
|
|
</ul>
|
|
</div>
|
|
|
|
<div class="document">
|
|
|
|
<div class="documentwrapper">
|
|
<div class="sphinxsidebar" role="navigation" aria-label="main navigation">
|
|
<div class="sphinxsidebarwrapper">
|
|
<search id="searchbox" style="display: none" role="search">
|
|
<h3 id="searchlabel">Quick search</h3>
|
|
<div class="searchformwrapper">
|
|
<form class="search" action="../../../search.html" method="get">
|
|
<input type="text" name="q" aria-labelledby="searchlabel" autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"/>
|
|
<input type="submit" value="Go" />
|
|
</form>
|
|
</div>
|
|
</search>
|
|
<script>document.getElementById('searchbox').style.display = "block"</script><h3>Links</h3>
|
|
<ul>
|
|
<li><a href="https://www.evennia.com/docs/latest/index.html">Documentation Top</a> </li>
|
|
<li><a href="https://www.evennia.com">Evennia Home</a> </li>
|
|
<li><a href="https://github.com/evennia/evennia">Github</a> </li>
|
|
<li><a href="http://games.evennia.com">Game Index</a> </li>
|
|
<li>
|
|
<a href="https://discord.gg/AJJpcRUhtF">Discord</a> -
|
|
<a href="https://github.com/evennia/evennia/discussions">Discussions</a> -
|
|
<a href="https://evennia.blogspot.com/">Blog</a>
|
|
</li>
|
|
</ul>
|
|
</div>
|
|
</div>
|
|
<div class="bodywrapper">
|
|
<div class="body" role="main">
|
|
|
|
<h1>Source code for django.utils.http</h1><div class="highlight"><pre>
|
|
<span></span><span class="kn">import</span><span class="w"> </span><span class="nn">base64</span>
|
|
<span class="kn">import</span><span class="w"> </span><span class="nn">re</span>
|
|
<span class="kn">import</span><span class="w"> </span><span class="nn">unicodedata</span>
|
|
<span class="kn">from</span><span class="w"> </span><span class="nn">binascii</span><span class="w"> </span><span class="kn">import</span> <span class="n">Error</span> <span class="k">as</span> <span class="n">BinasciiError</span>
|
|
<span class="kn">from</span><span class="w"> </span><span class="nn">datetime</span><span class="w"> </span><span class="kn">import</span> <span class="n">datetime</span><span class="p">,</span> <span class="n">timezone</span>
|
|
<span class="kn">from</span><span class="w"> </span><span class="nn">email.utils</span><span class="w"> </span><span class="kn">import</span> <span class="n">formatdate</span>
|
|
<span class="kn">from</span><span class="w"> </span><span class="nn">urllib.parse</span><span class="w"> </span><span class="kn">import</span> <span class="n">quote</span><span class="p">,</span> <span class="n">unquote</span>
|
|
<span class="kn">from</span><span class="w"> </span><span class="nn">urllib.parse</span><span class="w"> </span><span class="kn">import</span> <span class="n">urlencode</span> <span class="k">as</span> <span class="n">original_urlencode</span>
|
|
<span class="kn">from</span><span class="w"> </span><span class="nn">urllib.parse</span><span class="w"> </span><span class="kn">import</span> <span class="n">urlparse</span>
|
|
|
|
<span class="kn">from</span><span class="w"> </span><span class="nn">django.utils.datastructures</span><span class="w"> </span><span class="kn">import</span> <span class="n">MultiValueDict</span>
|
|
<span class="kn">from</span><span class="w"> </span><span class="nn">django.utils.regex_helper</span><span class="w"> </span><span class="kn">import</span> <span class="n">_lazy_re_compile</span>
|
|
|
|
<span class="c1"># Based on RFC 9110 Appendix A.</span>
|
|
<span class="n">ETAG_MATCH</span> <span class="o">=</span> <span class="n">_lazy_re_compile</span><span class="p">(</span>
|
|
<span class="w"> </span><span class="sa">r</span><span class="sd">"""</span>
|
|
<span class="sd"> \A( # start of string and capture group</span>
|
|
<span class="sd"> (?:W/)? # optional weak indicator</span>
|
|
<span class="sd"> " # opening quote</span>
|
|
<span class="sd"> [^"]* # any sequence of non-quote characters</span>
|
|
<span class="sd"> " # end quote</span>
|
|
<span class="sd"> )\Z # end of string and capture group</span>
|
|
<span class="sd">"""</span><span class="p">,</span>
|
|
<span class="n">re</span><span class="o">.</span><span class="n">X</span><span class="p">,</span>
|
|
<span class="p">)</span>
|
|
|
|
<span class="n">MONTHS</span> <span class="o">=</span> <span class="s2">"jan feb mar apr may jun jul aug sep oct nov dec"</span><span class="o">.</span><span class="n">split</span><span class="p">()</span>
|
|
<span class="n">__D</span> <span class="o">=</span> <span class="sa">r</span><span class="s2">"(?P<day>[0-9]</span><span class="si">{2}</span><span class="s2">)"</span>
|
|
<span class="n">__D2</span> <span class="o">=</span> <span class="sa">r</span><span class="s2">"(?P<day>[ 0-9][0-9])"</span>
|
|
<span class="n">__M</span> <span class="o">=</span> <span class="sa">r</span><span class="s2">"(?P<mon>\w</span><span class="si">{3}</span><span class="s2">)"</span>
|
|
<span class="n">__Y</span> <span class="o">=</span> <span class="sa">r</span><span class="s2">"(?P<year>[0-9]</span><span class="si">{4}</span><span class="s2">)"</span>
|
|
<span class="n">__Y2</span> <span class="o">=</span> <span class="sa">r</span><span class="s2">"(?P<year>[0-9]</span><span class="si">{2}</span><span class="s2">)"</span>
|
|
<span class="n">__T</span> <span class="o">=</span> <span class="sa">r</span><span class="s2">"(?P<hour>[0-9]</span><span class="si">{2}</span><span class="s2">):(?P<min>[0-9]</span><span class="si">{2}</span><span class="s2">):(?P<sec>[0-9]</span><span class="si">{2}</span><span class="s2">)"</span>
|
|
<span class="n">RFC1123_DATE</span> <span class="o">=</span> <span class="n">_lazy_re_compile</span><span class="p">(</span><span class="sa">r</span><span class="s2">"^\w</span><span class="si">{3}</span><span class="s2">, </span><span class="si">%s</span><span class="s2"> </span><span class="si">%s</span><span class="s2"> </span><span class="si">%s</span><span class="s2"> </span><span class="si">%s</span><span class="s2"> GMT$"</span> <span class="o">%</span> <span class="p">(</span><span class="n">__D</span><span class="p">,</span> <span class="n">__M</span><span class="p">,</span> <span class="n">__Y</span><span class="p">,</span> <span class="n">__T</span><span class="p">))</span>
|
|
<span class="n">RFC850_DATE</span> <span class="o">=</span> <span class="n">_lazy_re_compile</span><span class="p">(</span><span class="sa">r</span><span class="s2">"^\w{6,9}, </span><span class="si">%s</span><span class="s2">-</span><span class="si">%s</span><span class="s2">-</span><span class="si">%s</span><span class="s2"> </span><span class="si">%s</span><span class="s2"> GMT$"</span> <span class="o">%</span> <span class="p">(</span><span class="n">__D</span><span class="p">,</span> <span class="n">__M</span><span class="p">,</span> <span class="n">__Y2</span><span class="p">,</span> <span class="n">__T</span><span class="p">))</span>
|
|
<span class="n">ASCTIME_DATE</span> <span class="o">=</span> <span class="n">_lazy_re_compile</span><span class="p">(</span><span class="sa">r</span><span class="s2">"^\w</span><span class="si">{3}</span><span class="s2"> </span><span class="si">%s</span><span class="s2"> </span><span class="si">%s</span><span class="s2"> </span><span class="si">%s</span><span class="s2"> </span><span class="si">%s</span><span class="s2">$"</span> <span class="o">%</span> <span class="p">(</span><span class="n">__M</span><span class="p">,</span> <span class="n">__D2</span><span class="p">,</span> <span class="n">__T</span><span class="p">,</span> <span class="n">__Y</span><span class="p">))</span>
|
|
|
|
<span class="n">RFC3986_GENDELIMS</span> <span class="o">=</span> <span class="s2">":/?#[]@"</span>
|
|
<span class="n">RFC3986_SUBDELIMS</span> <span class="o">=</span> <span class="s2">"!$&'()*+,;="</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">urlencode</span><span class="p">(</span><span class="n">query</span><span class="p">,</span> <span class="n">doseq</span><span class="o">=</span><span class="kc">False</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> A version of Python's urllib.parse.urlencode() function that can operate on</span>
|
|
<span class="sd"> MultiValueDict and non-string values.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">query</span><span class="p">,</span> <span class="n">MultiValueDict</span><span class="p">):</span>
|
|
<span class="n">query</span> <span class="o">=</span> <span class="n">query</span><span class="o">.</span><span class="n">lists</span><span class="p">()</span>
|
|
<span class="k">elif</span> <span class="nb">hasattr</span><span class="p">(</span><span class="n">query</span><span class="p">,</span> <span class="s2">"items"</span><span class="p">):</span>
|
|
<span class="n">query</span> <span class="o">=</span> <span class="n">query</span><span class="o">.</span><span class="n">items</span><span class="p">()</span>
|
|
<span class="n">query_params</span> <span class="o">=</span> <span class="p">[]</span>
|
|
<span class="k">for</span> <span class="n">key</span><span class="p">,</span> <span class="n">value</span> <span class="ow">in</span> <span class="n">query</span><span class="p">:</span>
|
|
<span class="k">if</span> <span class="n">value</span> <span class="ow">is</span> <span class="kc">None</span><span class="p">:</span>
|
|
<span class="k">raise</span> <span class="ne">TypeError</span><span class="p">(</span>
|
|
<span class="s2">"Cannot encode None for key '</span><span class="si">%s</span><span class="s2">' in a query string. Did you "</span>
|
|
<span class="s2">"mean to pass an empty string or omit the value?"</span> <span class="o">%</span> <span class="n">key</span>
|
|
<span class="p">)</span>
|
|
<span class="k">elif</span> <span class="ow">not</span> <span class="n">doseq</span> <span class="ow">or</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">value</span><span class="p">,</span> <span class="p">(</span><span class="nb">str</span><span class="p">,</span> <span class="nb">bytes</span><span class="p">)):</span>
|
|
<span class="n">query_val</span> <span class="o">=</span> <span class="n">value</span>
|
|
<span class="k">else</span><span class="p">:</span>
|
|
<span class="k">try</span><span class="p">:</span>
|
|
<span class="n">itr</span> <span class="o">=</span> <span class="nb">iter</span><span class="p">(</span><span class="n">value</span><span class="p">)</span>
|
|
<span class="k">except</span> <span class="ne">TypeError</span><span class="p">:</span>
|
|
<span class="n">query_val</span> <span class="o">=</span> <span class="n">value</span>
|
|
<span class="k">else</span><span class="p">:</span>
|
|
<span class="c1"># Consume generators and iterators, when doseq=True, to</span>
|
|
<span class="c1"># work around https://bugs.python.org/issue31706.</span>
|
|
<span class="n">query_val</span> <span class="o">=</span> <span class="p">[]</span>
|
|
<span class="k">for</span> <span class="n">item</span> <span class="ow">in</span> <span class="n">itr</span><span class="p">:</span>
|
|
<span class="k">if</span> <span class="n">item</span> <span class="ow">is</span> <span class="kc">None</span><span class="p">:</span>
|
|
<span class="k">raise</span> <span class="ne">TypeError</span><span class="p">(</span>
|
|
<span class="s2">"Cannot encode None for key '</span><span class="si">%s</span><span class="s2">' in a query "</span>
|
|
<span class="s2">"string. Did you mean to pass an empty string or "</span>
|
|
<span class="s2">"omit the value?"</span> <span class="o">%</span> <span class="n">key</span>
|
|
<span class="p">)</span>
|
|
<span class="k">elif</span> <span class="ow">not</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">item</span><span class="p">,</span> <span class="nb">bytes</span><span class="p">):</span>
|
|
<span class="n">item</span> <span class="o">=</span> <span class="nb">str</span><span class="p">(</span><span class="n">item</span><span class="p">)</span>
|
|
<span class="n">query_val</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">item</span><span class="p">)</span>
|
|
<span class="n">query_params</span><span class="o">.</span><span class="n">append</span><span class="p">((</span><span class="n">key</span><span class="p">,</span> <span class="n">query_val</span><span class="p">))</span>
|
|
<span class="k">return</span> <span class="n">original_urlencode</span><span class="p">(</span><span class="n">query_params</span><span class="p">,</span> <span class="n">doseq</span><span class="p">)</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">http_date</span><span class="p">(</span><span class="n">epoch_seconds</span><span class="o">=</span><span class="kc">None</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> Format the time to match the RFC 5322 date format as specified by RFC 9110</span>
|
|
<span class="sd"> Section 5.6.7.</span>
|
|
|
|
<span class="sd"> `epoch_seconds` is a floating point number expressed in seconds since the</span>
|
|
<span class="sd"> epoch, in UTC - such as that outputted by time.time(). If set to None, it</span>
|
|
<span class="sd"> defaults to the current time.</span>
|
|
|
|
<span class="sd"> Output a string in the format 'Wdy, DD Mon YYYY HH:MM:SS GMT'.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="k">return</span> <span class="n">formatdate</span><span class="p">(</span><span class="n">epoch_seconds</span><span class="p">,</span> <span class="n">usegmt</span><span class="o">=</span><span class="kc">True</span><span class="p">)</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">parse_http_date</span><span class="p">(</span><span class="n">date</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> Parse a date format as specified by HTTP RFC 9110 Section 5.6.7.</span>
|
|
|
|
<span class="sd"> The three formats allowed by the RFC are accepted, even if only the first</span>
|
|
<span class="sd"> one is still in widespread use.</span>
|
|
|
|
<span class="sd"> Return an integer expressed in seconds since the epoch, in UTC.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="c1"># email.utils.parsedate() does the job for RFC 1123 dates; unfortunately</span>
|
|
<span class="c1"># RFC 9110 makes it mandatory to support RFC 850 dates too. So we roll</span>
|
|
<span class="c1"># our own RFC-compliant parsing.</span>
|
|
<span class="k">for</span> <span class="n">regex</span> <span class="ow">in</span> <span class="n">RFC1123_DATE</span><span class="p">,</span> <span class="n">RFC850_DATE</span><span class="p">,</span> <span class="n">ASCTIME_DATE</span><span class="p">:</span>
|
|
<span class="n">m</span> <span class="o">=</span> <span class="n">regex</span><span class="o">.</span><span class="n">match</span><span class="p">(</span><span class="n">date</span><span class="p">)</span>
|
|
<span class="k">if</span> <span class="n">m</span> <span class="ow">is</span> <span class="ow">not</span> <span class="kc">None</span><span class="p">:</span>
|
|
<span class="k">break</span>
|
|
<span class="k">else</span><span class="p">:</span>
|
|
<span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s2">"</span><span class="si">%r</span><span class="s2"> is not in a valid HTTP date format"</span> <span class="o">%</span> <span class="n">date</span><span class="p">)</span>
|
|
<span class="k">try</span><span class="p">:</span>
|
|
<span class="n">year</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">m</span><span class="p">[</span><span class="s2">"year"</span><span class="p">])</span>
|
|
<span class="k">if</span> <span class="n">year</span> <span class="o"><</span> <span class="mi">100</span><span class="p">:</span>
|
|
<span class="n">current_year</span> <span class="o">=</span> <span class="n">datetime</span><span class="o">.</span><span class="n">now</span><span class="p">(</span><span class="n">tz</span><span class="o">=</span><span class="n">timezone</span><span class="o">.</span><span class="n">utc</span><span class="p">)</span><span class="o">.</span><span class="n">year</span>
|
|
<span class="n">current_century</span> <span class="o">=</span> <span class="n">current_year</span> <span class="o">-</span> <span class="p">(</span><span class="n">current_year</span> <span class="o">%</span> <span class="mi">100</span><span class="p">)</span>
|
|
<span class="k">if</span> <span class="n">year</span> <span class="o">-</span> <span class="p">(</span><span class="n">current_year</span> <span class="o">%</span> <span class="mi">100</span><span class="p">)</span> <span class="o">></span> <span class="mi">50</span><span class="p">:</span>
|
|
<span class="c1"># year that appears to be more than 50 years in the future are</span>
|
|
<span class="c1"># interpreted as representing the past.</span>
|
|
<span class="n">year</span> <span class="o">+=</span> <span class="n">current_century</span> <span class="o">-</span> <span class="mi">100</span>
|
|
<span class="k">else</span><span class="p">:</span>
|
|
<span class="n">year</span> <span class="o">+=</span> <span class="n">current_century</span>
|
|
<span class="n">month</span> <span class="o">=</span> <span class="n">MONTHS</span><span class="o">.</span><span class="n">index</span><span class="p">(</span><span class="n">m</span><span class="p">[</span><span class="s2">"mon"</span><span class="p">]</span><span class="o">.</span><span class="n">lower</span><span class="p">())</span> <span class="o">+</span> <span class="mi">1</span>
|
|
<span class="n">day</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">m</span><span class="p">[</span><span class="s2">"day"</span><span class="p">])</span>
|
|
<span class="n">hour</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">m</span><span class="p">[</span><span class="s2">"hour"</span><span class="p">])</span>
|
|
<span class="nb">min</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">m</span><span class="p">[</span><span class="s2">"min"</span><span class="p">])</span>
|
|
<span class="n">sec</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">m</span><span class="p">[</span><span class="s2">"sec"</span><span class="p">])</span>
|
|
<span class="n">result</span> <span class="o">=</span> <span class="n">datetime</span><span class="p">(</span><span class="n">year</span><span class="p">,</span> <span class="n">month</span><span class="p">,</span> <span class="n">day</span><span class="p">,</span> <span class="n">hour</span><span class="p">,</span> <span class="nb">min</span><span class="p">,</span> <span class="n">sec</span><span class="p">,</span> <span class="n">tzinfo</span><span class="o">=</span><span class="n">timezone</span><span class="o">.</span><span class="n">utc</span><span class="p">)</span>
|
|
<span class="k">return</span> <span class="nb">int</span><span class="p">(</span><span class="n">result</span><span class="o">.</span><span class="n">timestamp</span><span class="p">())</span>
|
|
<span class="k">except</span> <span class="ne">Exception</span> <span class="k">as</span> <span class="n">exc</span><span class="p">:</span>
|
|
<span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s2">"</span><span class="si">%r</span><span class="s2"> is not a valid date"</span> <span class="o">%</span> <span class="n">date</span><span class="p">)</span> <span class="kn">from</span><span class="w"> </span><span class="nn">exc</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">parse_http_date_safe</span><span class="p">(</span><span class="n">date</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> Same as parse_http_date, but return None if the input is invalid.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="k">try</span><span class="p">:</span>
|
|
<span class="k">return</span> <span class="n">parse_http_date</span><span class="p">(</span><span class="n">date</span><span class="p">)</span>
|
|
<span class="k">except</span> <span class="ne">Exception</span><span class="p">:</span>
|
|
<span class="k">pass</span>
|
|
|
|
|
|
<span class="c1"># Base 36 functions: useful for generating compact URLs</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">base36_to_int</span><span class="p">(</span><span class="n">s</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> Convert a base 36 string to an int. Raise ValueError if the input won't fit</span>
|
|
<span class="sd"> into an int.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="c1"># To prevent overconsumption of server resources, reject any</span>
|
|
<span class="c1"># base36 string that is longer than 13 base36 digits (13 digits</span>
|
|
<span class="c1"># is sufficient to base36-encode any 64-bit integer)</span>
|
|
<span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">s</span><span class="p">)</span> <span class="o">></span> <span class="mi">13</span><span class="p">:</span>
|
|
<span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s2">"Base36 input too large"</span><span class="p">)</span>
|
|
<span class="k">return</span> <span class="nb">int</span><span class="p">(</span><span class="n">s</span><span class="p">,</span> <span class="mi">36</span><span class="p">)</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">int_to_base36</span><span class="p">(</span><span class="n">i</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""Convert an integer to a base36 string."""</span>
|
|
<span class="n">char_set</span> <span class="o">=</span> <span class="s2">"0123456789abcdefghijklmnopqrstuvwxyz"</span>
|
|
<span class="k">if</span> <span class="n">i</span> <span class="o"><</span> <span class="mi">0</span><span class="p">:</span>
|
|
<span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s2">"Negative base36 conversion input."</span><span class="p">)</span>
|
|
<span class="k">if</span> <span class="n">i</span> <span class="o"><</span> <span class="mi">36</span><span class="p">:</span>
|
|
<span class="k">return</span> <span class="n">char_set</span><span class="p">[</span><span class="n">i</span><span class="p">]</span>
|
|
<span class="n">b36</span> <span class="o">=</span> <span class="s2">""</span>
|
|
<span class="k">while</span> <span class="n">i</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">:</span>
|
|
<span class="n">i</span><span class="p">,</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">divmod</span><span class="p">(</span><span class="n">i</span><span class="p">,</span> <span class="mi">36</span><span class="p">)</span>
|
|
<span class="n">b36</span> <span class="o">=</span> <span class="n">char_set</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">b36</span>
|
|
<span class="k">return</span> <span class="n">b36</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">urlsafe_base64_encode</span><span class="p">(</span><span class="n">s</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> Encode a bytestring to a base64 string for use in URLs. Strip any trailing</span>
|
|
<span class="sd"> equal signs.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="k">return</span> <span class="n">base64</span><span class="o">.</span><span class="n">urlsafe_b64encode</span><span class="p">(</span><span class="n">s</span><span class="p">)</span><span class="o">.</span><span class="n">rstrip</span><span class="p">(</span><span class="sa">b</span><span class="s2">"</span><span class="se">\n</span><span class="s2">="</span><span class="p">)</span><span class="o">.</span><span class="n">decode</span><span class="p">(</span><span class="s2">"ascii"</span><span class="p">)</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">urlsafe_base64_decode</span><span class="p">(</span><span class="n">s</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> Decode a base64 encoded string. Add back any trailing equal signs that</span>
|
|
<span class="sd"> might have been stripped.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="n">s</span> <span class="o">=</span> <span class="n">s</span><span class="o">.</span><span class="n">encode</span><span class="p">()</span>
|
|
<span class="k">try</span><span class="p">:</span>
|
|
<span class="k">return</span> <span class="n">base64</span><span class="o">.</span><span class="n">urlsafe_b64decode</span><span class="p">(</span><span class="n">s</span><span class="o">.</span><span class="n">ljust</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">s</span><span class="p">)</span> <span class="o">+</span> <span class="nb">len</span><span class="p">(</span><span class="n">s</span><span class="p">)</span> <span class="o">%</span> <span class="mi">4</span><span class="p">,</span> <span class="sa">b</span><span class="s2">"="</span><span class="p">))</span>
|
|
<span class="k">except</span> <span class="p">(</span><span class="ne">LookupError</span><span class="p">,</span> <span class="n">BinasciiError</span><span class="p">)</span> <span class="k">as</span> <span class="n">e</span><span class="p">:</span>
|
|
<span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="n">e</span><span class="p">)</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">parse_etags</span><span class="p">(</span><span class="n">etag_str</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> Parse a string of ETags given in an If-None-Match or If-Match header as</span>
|
|
<span class="sd"> defined by RFC 9110. Return a list of quoted ETags, or ['*'] if all ETags</span>
|
|
<span class="sd"> should be matched.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="k">if</span> <span class="n">etag_str</span><span class="o">.</span><span class="n">strip</span><span class="p">()</span> <span class="o">==</span> <span class="s2">"*"</span><span class="p">:</span>
|
|
<span class="k">return</span> <span class="p">[</span><span class="s2">"*"</span><span class="p">]</span>
|
|
<span class="k">else</span><span class="p">:</span>
|
|
<span class="c1"># Parse each ETag individually, and return any that are valid.</span>
|
|
<span class="n">etag_matches</span> <span class="o">=</span> <span class="p">(</span><span class="n">ETAG_MATCH</span><span class="o">.</span><span class="n">match</span><span class="p">(</span><span class="n">etag</span><span class="o">.</span><span class="n">strip</span><span class="p">())</span> <span class="k">for</span> <span class="n">etag</span> <span class="ow">in</span> <span class="n">etag_str</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s2">","</span><span class="p">))</span>
|
|
<span class="k">return</span> <span class="p">[</span><span class="n">match</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="k">for</span> <span class="n">match</span> <span class="ow">in</span> <span class="n">etag_matches</span> <span class="k">if</span> <span class="n">match</span><span class="p">]</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">quote_etag</span><span class="p">(</span><span class="n">etag_str</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> If the provided string is already a quoted ETag, return it. Otherwise, wrap</span>
|
|
<span class="sd"> the string in quotes, making it a strong ETag.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="k">if</span> <span class="n">ETAG_MATCH</span><span class="o">.</span><span class="n">match</span><span class="p">(</span><span class="n">etag_str</span><span class="p">):</span>
|
|
<span class="k">return</span> <span class="n">etag_str</span>
|
|
<span class="k">else</span><span class="p">:</span>
|
|
<span class="k">return</span> <span class="s1">'"</span><span class="si">%s</span><span class="s1">"'</span> <span class="o">%</span> <span class="n">etag_str</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">is_same_domain</span><span class="p">(</span><span class="n">host</span><span class="p">,</span> <span class="n">pattern</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> Return ``True`` if the host is either an exact match or a match</span>
|
|
<span class="sd"> to the wildcard pattern.</span>
|
|
|
|
<span class="sd"> Any pattern beginning with a period matches a domain and all of its</span>
|
|
<span class="sd"> subdomains. (e.g. ``.example.com`` matches ``example.com`` and</span>
|
|
<span class="sd"> ``foo.example.com``). Anything else is an exact string match.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="k">if</span> <span class="ow">not</span> <span class="n">pattern</span><span class="p">:</span>
|
|
<span class="k">return</span> <span class="kc">False</span>
|
|
|
|
<span class="n">pattern</span> <span class="o">=</span> <span class="n">pattern</span><span class="o">.</span><span class="n">lower</span><span class="p">()</span>
|
|
<span class="k">return</span> <span class="p">(</span>
|
|
<span class="n">pattern</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="s2">"."</span>
|
|
<span class="ow">and</span> <span class="p">(</span><span class="n">host</span><span class="o">.</span><span class="n">endswith</span><span class="p">(</span><span class="n">pattern</span><span class="p">)</span> <span class="ow">or</span> <span class="n">host</span> <span class="o">==</span> <span class="n">pattern</span><span class="p">[</span><span class="mi">1</span><span class="p">:])</span>
|
|
<span class="ow">or</span> <span class="n">pattern</span> <span class="o">==</span> <span class="n">host</span>
|
|
<span class="p">)</span>
|
|
|
|
|
|
<div class="viewcode-block" id="url_has_allowed_host_and_scheme">
|
|
<a class="viewcode-back" href="../../../api/evennia.web.website.views.characters.html#evennia.web.website.views.characters.url_has_allowed_host_and_scheme">[docs]</a>
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">url_has_allowed_host_and_scheme</span><span class="p">(</span><span class="n">url</span><span class="p">,</span> <span class="n">allowed_hosts</span><span class="p">,</span> <span class="n">require_https</span><span class="o">=</span><span class="kc">False</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> Return ``True`` if the url uses an allowed host and a safe scheme.</span>
|
|
|
|
<span class="sd"> Always return ``False`` on an empty url.</span>
|
|
|
|
<span class="sd"> If ``require_https`` is ``True``, only 'https' will be considered a valid</span>
|
|
<span class="sd"> scheme, as opposed to 'http' and 'https' with the default, ``False``.</span>
|
|
|
|
<span class="sd"> Note: "True" doesn't entail that a URL is "safe". It may still be e.g.</span>
|
|
<span class="sd"> quoted incorrectly. Ensure to also use django.utils.encoding.iri_to_uri()</span>
|
|
<span class="sd"> on the path component of untrusted URLs.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="k">if</span> <span class="n">url</span> <span class="ow">is</span> <span class="ow">not</span> <span class="kc">None</span><span class="p">:</span>
|
|
<span class="n">url</span> <span class="o">=</span> <span class="n">url</span><span class="o">.</span><span class="n">strip</span><span class="p">()</span>
|
|
<span class="k">if</span> <span class="ow">not</span> <span class="n">url</span><span class="p">:</span>
|
|
<span class="k">return</span> <span class="kc">False</span>
|
|
<span class="k">if</span> <span class="n">allowed_hosts</span> <span class="ow">is</span> <span class="kc">None</span><span class="p">:</span>
|
|
<span class="n">allowed_hosts</span> <span class="o">=</span> <span class="nb">set</span><span class="p">()</span>
|
|
<span class="k">elif</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">allowed_hosts</span><span class="p">,</span> <span class="nb">str</span><span class="p">):</span>
|
|
<span class="n">allowed_hosts</span> <span class="o">=</span> <span class="p">{</span><span class="n">allowed_hosts</span><span class="p">}</span>
|
|
<span class="c1"># Chrome treats \ completely as / in paths but it could be part of some</span>
|
|
<span class="c1"># basic auth credentials so we need to check both URLs.</span>
|
|
<span class="k">return</span> <span class="n">_url_has_allowed_host_and_scheme</span><span class="p">(</span>
|
|
<span class="n">url</span><span class="p">,</span> <span class="n">allowed_hosts</span><span class="p">,</span> <span class="n">require_https</span><span class="o">=</span><span class="n">require_https</span>
|
|
<span class="p">)</span> <span class="ow">and</span> <span class="n">_url_has_allowed_host_and_scheme</span><span class="p">(</span>
|
|
<span class="n">url</span><span class="o">.</span><span class="n">replace</span><span class="p">(</span><span class="s2">"</span><span class="se">\\</span><span class="s2">"</span><span class="p">,</span> <span class="s2">"/"</span><span class="p">),</span> <span class="n">allowed_hosts</span><span class="p">,</span> <span class="n">require_https</span><span class="o">=</span><span class="n">require_https</span>
|
|
<span class="p">)</span></div>
|
|
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">_url_has_allowed_host_and_scheme</span><span class="p">(</span><span class="n">url</span><span class="p">,</span> <span class="n">allowed_hosts</span><span class="p">,</span> <span class="n">require_https</span><span class="o">=</span><span class="kc">False</span><span class="p">):</span>
|
|
<span class="c1"># Chrome considers any URL with more than two slashes to be absolute, but</span>
|
|
<span class="c1"># urlparse is not so flexible. Treat any url with three slashes as unsafe.</span>
|
|
<span class="k">if</span> <span class="n">url</span><span class="o">.</span><span class="n">startswith</span><span class="p">(</span><span class="s2">"///"</span><span class="p">):</span>
|
|
<span class="k">return</span> <span class="kc">False</span>
|
|
<span class="k">try</span><span class="p">:</span>
|
|
<span class="n">url_info</span> <span class="o">=</span> <span class="n">urlparse</span><span class="p">(</span><span class="n">url</span><span class="p">)</span>
|
|
<span class="k">except</span> <span class="ne">ValueError</span><span class="p">:</span> <span class="c1"># e.g. invalid IPv6 addresses</span>
|
|
<span class="k">return</span> <span class="kc">False</span>
|
|
<span class="c1"># Forbid URLs like http:///example.com - with a scheme, but without a hostname.</span>
|
|
<span class="c1"># In that URL, example.com is not the hostname but, a path component. However,</span>
|
|
<span class="c1"># Chrome will still consider example.com to be the hostname, so we must not</span>
|
|
<span class="c1"># allow this syntax.</span>
|
|
<span class="k">if</span> <span class="ow">not</span> <span class="n">url_info</span><span class="o">.</span><span class="n">netloc</span> <span class="ow">and</span> <span class="n">url_info</span><span class="o">.</span><span class="n">scheme</span><span class="p">:</span>
|
|
<span class="k">return</span> <span class="kc">False</span>
|
|
<span class="c1"># Forbid URLs that start with control characters. Some browsers (like</span>
|
|
<span class="c1"># Chrome) ignore quite a few control characters at the start of a</span>
|
|
<span class="c1"># URL and might consider the URL as scheme relative.</span>
|
|
<span class="k">if</span> <span class="n">unicodedata</span><span class="o">.</span><span class="n">category</span><span class="p">(</span><span class="n">url</span><span class="p">[</span><span class="mi">0</span><span class="p">])[</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="s2">"C"</span><span class="p">:</span>
|
|
<span class="k">return</span> <span class="kc">False</span>
|
|
<span class="n">scheme</span> <span class="o">=</span> <span class="n">url_info</span><span class="o">.</span><span class="n">scheme</span>
|
|
<span class="c1"># Consider URLs without a scheme (e.g. //example.com/p) to be http.</span>
|
|
<span class="k">if</span> <span class="ow">not</span> <span class="n">url_info</span><span class="o">.</span><span class="n">scheme</span> <span class="ow">and</span> <span class="n">url_info</span><span class="o">.</span><span class="n">netloc</span><span class="p">:</span>
|
|
<span class="n">scheme</span> <span class="o">=</span> <span class="s2">"http"</span>
|
|
<span class="n">valid_schemes</span> <span class="o">=</span> <span class="p">[</span><span class="s2">"https"</span><span class="p">]</span> <span class="k">if</span> <span class="n">require_https</span> <span class="k">else</span> <span class="p">[</span><span class="s2">"http"</span><span class="p">,</span> <span class="s2">"https"</span><span class="p">]</span>
|
|
<span class="k">return</span> <span class="p">(</span><span class="ow">not</span> <span class="n">url_info</span><span class="o">.</span><span class="n">netloc</span> <span class="ow">or</span> <span class="n">url_info</span><span class="o">.</span><span class="n">netloc</span> <span class="ow">in</span> <span class="n">allowed_hosts</span><span class="p">)</span> <span class="ow">and</span> <span class="p">(</span>
|
|
<span class="ow">not</span> <span class="n">scheme</span> <span class="ow">or</span> <span class="n">scheme</span> <span class="ow">in</span> <span class="n">valid_schemes</span>
|
|
<span class="p">)</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">escape_leading_slashes</span><span class="p">(</span><span class="n">url</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> If redirecting to an absolute path (two leading slashes), a slash must be</span>
|
|
<span class="sd"> escaped to prevent browsers from handling the path as schemaless and</span>
|
|
<span class="sd"> redirecting to another host.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="k">if</span> <span class="n">url</span><span class="o">.</span><span class="n">startswith</span><span class="p">(</span><span class="s2">"//"</span><span class="p">):</span>
|
|
<span class="n">url</span> <span class="o">=</span> <span class="s2">"/</span><span class="si">%2F{}</span><span class="s2">"</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">url</span><span class="o">.</span><span class="n">removeprefix</span><span class="p">(</span><span class="s2">"//"</span><span class="p">))</span>
|
|
<span class="k">return</span> <span class="n">url</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">_parseparam</span><span class="p">(</span><span class="n">s</span><span class="p">):</span>
|
|
<span class="k">while</span> <span class="n">s</span><span class="p">[:</span><span class="mi">1</span><span class="p">]</span> <span class="o">==</span> <span class="s2">";"</span><span class="p">:</span>
|
|
<span class="n">s</span> <span class="o">=</span> <span class="n">s</span><span class="p">[</span><span class="mi">1</span><span class="p">:]</span>
|
|
<span class="n">end</span> <span class="o">=</span> <span class="n">s</span><span class="o">.</span><span class="n">find</span><span class="p">(</span><span class="s2">";"</span><span class="p">)</span>
|
|
<span class="k">while</span> <span class="n">end</span> <span class="o">></span> <span class="mi">0</span> <span class="ow">and</span> <span class="p">(</span><span class="n">s</span><span class="o">.</span><span class="n">count</span><span class="p">(</span><span class="s1">'"'</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="n">end</span><span class="p">)</span> <span class="o">-</span> <span class="n">s</span><span class="o">.</span><span class="n">count</span><span class="p">(</span><span class="s1">'</span><span class="se">\\</span><span class="s1">"'</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="n">end</span><span class="p">))</span> <span class="o">%</span> <span class="mi">2</span><span class="p">:</span>
|
|
<span class="n">end</span> <span class="o">=</span> <span class="n">s</span><span class="o">.</span><span class="n">find</span><span class="p">(</span><span class="s2">";"</span><span class="p">,</span> <span class="n">end</span> <span class="o">+</span> <span class="mi">1</span><span class="p">)</span>
|
|
<span class="k">if</span> <span class="n">end</span> <span class="o"><</span> <span class="mi">0</span><span class="p">:</span>
|
|
<span class="n">end</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">s</span><span class="p">)</span>
|
|
<span class="n">f</span> <span class="o">=</span> <span class="n">s</span><span class="p">[:</span><span class="n">end</span><span class="p">]</span>
|
|
<span class="k">yield</span> <span class="n">f</span><span class="o">.</span><span class="n">strip</span><span class="p">()</span>
|
|
<span class="n">s</span> <span class="o">=</span> <span class="n">s</span><span class="p">[</span><span class="n">end</span><span class="p">:]</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">parse_header_parameters</span><span class="p">(</span><span class="n">line</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> Parse a Content-type like header.</span>
|
|
<span class="sd"> Return the main content-type and a dictionary of options.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="n">parts</span> <span class="o">=</span> <span class="n">_parseparam</span><span class="p">(</span><span class="s2">";"</span> <span class="o">+</span> <span class="n">line</span><span class="p">)</span>
|
|
<span class="n">key</span> <span class="o">=</span> <span class="n">parts</span><span class="o">.</span><span class="fm">__next__</span><span class="p">()</span><span class="o">.</span><span class="n">lower</span><span class="p">()</span>
|
|
<span class="n">pdict</span> <span class="o">=</span> <span class="p">{}</span>
|
|
<span class="k">for</span> <span class="n">p</span> <span class="ow">in</span> <span class="n">parts</span><span class="p">:</span>
|
|
<span class="n">i</span> <span class="o">=</span> <span class="n">p</span><span class="o">.</span><span class="n">find</span><span class="p">(</span><span class="s2">"="</span><span class="p">)</span>
|
|
<span class="k">if</span> <span class="n">i</span> <span class="o">>=</span> <span class="mi">0</span><span class="p">:</span>
|
|
<span class="n">has_encoding</span> <span class="o">=</span> <span class="kc">False</span>
|
|
<span class="n">name</span> <span class="o">=</span> <span class="n">p</span><span class="p">[:</span><span class="n">i</span><span class="p">]</span><span class="o">.</span><span class="n">strip</span><span class="p">()</span><span class="o">.</span><span class="n">lower</span><span class="p">()</span>
|
|
<span class="k">if</span> <span class="n">name</span><span class="o">.</span><span class="n">endswith</span><span class="p">(</span><span class="s2">"*"</span><span class="p">):</span>
|
|
<span class="c1"># Lang/encoding embedded in the value (like "filename*=UTF-8''file.ext")</span>
|
|
<span class="c1"># https://tools.ietf.org/html/rfc2231#section-4</span>
|
|
<span class="n">name</span> <span class="o">=</span> <span class="n">name</span><span class="p">[:</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
|
|
<span class="k">if</span> <span class="n">p</span><span class="o">.</span><span class="n">count</span><span class="p">(</span><span class="s2">"'"</span><span class="p">)</span> <span class="o">==</span> <span class="mi">2</span><span class="p">:</span>
|
|
<span class="n">has_encoding</span> <span class="o">=</span> <span class="kc">True</span>
|
|
<span class="n">value</span> <span class="o">=</span> <span class="n">p</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="mi">1</span> <span class="p">:]</span><span class="o">.</span><span class="n">strip</span><span class="p">()</span>
|
|
<span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">value</span><span class="p">)</span> <span class="o">>=</span> <span class="mi">2</span> <span class="ow">and</span> <span class="n">value</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="n">value</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="o">==</span> <span class="s1">'"'</span><span class="p">:</span>
|
|
<span class="n">value</span> <span class="o">=</span> <span class="n">value</span><span class="p">[</span><span class="mi">1</span><span class="p">:</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
|
|
<span class="n">value</span> <span class="o">=</span> <span class="n">value</span><span class="o">.</span><span class="n">replace</span><span class="p">(</span><span class="s2">"</span><span class="se">\\\\</span><span class="s2">"</span><span class="p">,</span> <span class="s2">"</span><span class="se">\\</span><span class="s2">"</span><span class="p">)</span><span class="o">.</span><span class="n">replace</span><span class="p">(</span><span class="s1">'</span><span class="se">\\</span><span class="s1">"'</span><span class="p">,</span> <span class="s1">'"'</span><span class="p">)</span>
|
|
<span class="k">if</span> <span class="n">has_encoding</span><span class="p">:</span>
|
|
<span class="n">encoding</span><span class="p">,</span> <span class="n">lang</span><span class="p">,</span> <span class="n">value</span> <span class="o">=</span> <span class="n">value</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s2">"'"</span><span class="p">)</span>
|
|
<span class="n">value</span> <span class="o">=</span> <span class="n">unquote</span><span class="p">(</span><span class="n">value</span><span class="p">,</span> <span class="n">encoding</span><span class="o">=</span><span class="n">encoding</span><span class="p">)</span>
|
|
<span class="n">pdict</span><span class="p">[</span><span class="n">name</span><span class="p">]</span> <span class="o">=</span> <span class="n">value</span>
|
|
<span class="k">return</span> <span class="n">key</span><span class="p">,</span> <span class="n">pdict</span>
|
|
|
|
|
|
<span class="k">def</span><span class="w"> </span><span class="nf">content_disposition_header</span><span class="p">(</span><span class="n">as_attachment</span><span class="p">,</span> <span class="n">filename</span><span class="p">):</span>
|
|
<span class="w"> </span><span class="sd">"""</span>
|
|
<span class="sd"> Construct a Content-Disposition HTTP header value from the given filename</span>
|
|
<span class="sd"> as specified by RFC 6266.</span>
|
|
<span class="sd"> """</span>
|
|
<span class="k">if</span> <span class="n">filename</span><span class="p">:</span>
|
|
<span class="n">disposition</span> <span class="o">=</span> <span class="s2">"attachment"</span> <span class="k">if</span> <span class="n">as_attachment</span> <span class="k">else</span> <span class="s2">"inline"</span>
|
|
<span class="k">try</span><span class="p">:</span>
|
|
<span class="n">filename</span><span class="o">.</span><span class="n">encode</span><span class="p">(</span><span class="s2">"ascii"</span><span class="p">)</span>
|
|
<span class="n">file_expr</span> <span class="o">=</span> <span class="s1">'filename="</span><span class="si">{}</span><span class="s1">"'</span><span class="o">.</span><span class="n">format</span><span class="p">(</span>
|
|
<span class="n">filename</span><span class="o">.</span><span class="n">replace</span><span class="p">(</span><span class="s2">"</span><span class="se">\\</span><span class="s2">"</span><span class="p">,</span> <span class="s2">"</span><span class="se">\\\\</span><span class="s2">"</span><span class="p">)</span><span class="o">.</span><span class="n">replace</span><span class="p">(</span><span class="s1">'"'</span><span class="p">,</span> <span class="sa">r</span><span class="s2">"</span><span class="se">\"</span><span class="s2">"</span><span class="p">)</span>
|
|
<span class="p">)</span>
|
|
<span class="k">except</span> <span class="ne">UnicodeEncodeError</span><span class="p">:</span>
|
|
<span class="n">file_expr</span> <span class="o">=</span> <span class="s2">"filename*=utf-8''</span><span class="si">{}</span><span class="s2">"</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">quote</span><span class="p">(</span><span class="n">filename</span><span class="p">))</span>
|
|
<span class="k">return</span> <span class="sa">f</span><span class="s2">"</span><span class="si">{</span><span class="n">disposition</span><span class="si">}</span><span class="s2">; </span><span class="si">{</span><span class="n">file_expr</span><span class="si">}</span><span class="s2">"</span>
|
|
<span class="k">elif</span> <span class="n">as_attachment</span><span class="p">:</span>
|
|
<span class="k">return</span> <span class="s2">"attachment"</span>
|
|
<span class="k">else</span><span class="p">:</span>
|
|
<span class="k">return</span> <span class="kc">None</span>
|
|
</pre></div>
|
|
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
</div>
|
|
<div class="related" role="navigation" aria-label="related navigation">
|
|
<h3>Navigation</h3>
|
|
<ul>
|
|
<li class="right" style="margin-right: 10px">
|
|
<a href="../../../genindex.html" title="General Index"
|
|
>index</a></li>
|
|
<li class="right" >
|
|
<a href="../../../py-modindex.html" title="Python Module Index"
|
|
>modules</a> |</li>
|
|
<li class="nav-item nav-item-0"><a href="../../../index.html">Evennia latest</a> »</li>
|
|
<li class="nav-item nav-item-1"><a href="../../index.html" >Module code</a> »</li>
|
|
<li class="nav-item nav-item-this"><a href="">django.utils.http</a></li>
|
|
</ul>
|
|
</div>
|
|
|
|
|
|
|
|
<div class="footer" role="contentinfo">
|
|
© Copyright 2024, The Evennia developer community.
|
|
Created using <a href="https://www.sphinx-doc.org/">Sphinx</a> 8.2.3.
|
|
</div>
|
|
</body>
|
|
</html> |