mirror of
https://github.com/Tautulli/Tautulli.git
synced 2025-08-14 02:26:58 -07:00
Update CherryPy to 5.1.0
This commit is contained in:
parent
f9825410dc
commit
b2304992e5
25 changed files with 2383 additions and 130 deletions
|
@ -23,10 +23,11 @@ __date__ = 'April 2009'
|
|||
|
||||
|
||||
import time
|
||||
from hashlib import md5
|
||||
from cherrypy._cpcompat import parse_http_list, parse_keqv_list
|
||||
|
||||
import cherrypy
|
||||
from cherrypy._cpcompat import md5, ntob
|
||||
from cherrypy._cpcompat import ntob
|
||||
md5_hex = lambda s: md5(ntob(s)).hexdigest()
|
||||
|
||||
qop_auth = 'auth'
|
||||
|
|
|
@ -210,6 +210,7 @@ def extrapolate_statistics(scope):
|
|||
|
||||
# -------------------- CherryPy Applications Statistics --------------------- #
|
||||
|
||||
import sys
|
||||
import threading
|
||||
import time
|
||||
|
||||
|
@ -294,6 +295,11 @@ class ByteCountWrapper(object):
|
|||
average_uriset_time = lambda s: s['Count'] and (s['Sum'] / s['Count']) or 0
|
||||
|
||||
|
||||
def _get_threading_ident():
|
||||
if sys.version_info >= (3, 3):
|
||||
return threading.get_ident()
|
||||
return threading._get_ident()
|
||||
|
||||
class StatsTool(cherrypy.Tool):
|
||||
|
||||
"""Record various information about the current request."""
|
||||
|
@ -322,7 +328,7 @@ class StatsTool(cherrypy.Tool):
|
|||
|
||||
appstats['Current Requests'] += 1
|
||||
appstats['Total Requests'] += 1
|
||||
appstats['Requests'][threading._get_ident()] = {
|
||||
appstats['Requests'][_get_threading_ident()] = {
|
||||
'Bytes Read': None,
|
||||
'Bytes Written': None,
|
||||
# Use a lambda so the ip gets updated by tools.proxy later
|
||||
|
@ -339,7 +345,7 @@ class StatsTool(cherrypy.Tool):
|
|||
debug=False, **kwargs):
|
||||
"""Record the end of a request."""
|
||||
resp = cherrypy.serving.response
|
||||
w = appstats['Requests'][threading._get_ident()]
|
||||
w = appstats['Requests'][_get_threading_ident()]
|
||||
|
||||
r = cherrypy.request.rfile.bytes_read
|
||||
w['Bytes Read'] = r
|
||||
|
@ -605,7 +611,13 @@ table.stats2 th {
|
|||
"""Return ([headers], [rows]) for the given collection."""
|
||||
# E.g., the 'Requests' dict.
|
||||
headers = []
|
||||
for record in v.itervalues():
|
||||
try:
|
||||
# python2
|
||||
vals = v.itervalues()
|
||||
except AttributeError:
|
||||
# python3
|
||||
vals = v.values()
|
||||
for record in vals:
|
||||
for k3 in record:
|
||||
format = formatting.get(k3, missing)
|
||||
if format is None:
|
||||
|
|
|
@ -2,9 +2,10 @@
|
|||
|
||||
import logging
|
||||
import re
|
||||
from hashlib import md5
|
||||
|
||||
import cherrypy
|
||||
from cherrypy._cpcompat import basestring, md5, set, unicodestr
|
||||
from cherrypy._cpcompat import basestring, unicodestr
|
||||
from cherrypy.lib import httputil as _httputil
|
||||
from cherrypy.lib import is_iterator
|
||||
|
||||
|
@ -192,11 +193,10 @@ def proxy(base=None, local='X-Forwarded-Host', remote='X-Forwarded-For',
|
|||
if lbase is not None:
|
||||
base = lbase.split(',')[0]
|
||||
if not base:
|
||||
base = request.headers.get('Host', '127.0.0.1')
|
||||
port = request.local.port
|
||||
if port == 80:
|
||||
base = '127.0.0.1'
|
||||
else:
|
||||
base = '127.0.0.1:%s' % port
|
||||
if port != 80:
|
||||
base += ':%s' % port
|
||||
|
||||
if base.find("://") == -1:
|
||||
# add http:// or https:// if needed
|
||||
|
|
|
@ -2,7 +2,7 @@ import struct
|
|||
import time
|
||||
|
||||
import cherrypy
|
||||
from cherrypy._cpcompat import basestring, BytesIO, ntob, set, unicodestr
|
||||
from cherrypy._cpcompat import basestring, BytesIO, ntob, unicodestr
|
||||
from cherrypy.lib import file_generator
|
||||
from cherrypy.lib import is_closable_iterator
|
||||
from cherrypy.lib import set_vary_header
|
||||
|
|
|
@ -62,7 +62,9 @@ __all__ = ("digestAuth", "basicAuth", "doAuth", "checkResponse",
|
|||
|
||||
##########################################################################
|
||||
import time
|
||||
from cherrypy._cpcompat import base64_decode, ntob, md5
|
||||
from hashlib import md5
|
||||
|
||||
from cherrypy._cpcompat import base64_decode, ntob
|
||||
from cherrypy._cpcompat import parse_http_list, parse_keqv_list
|
||||
|
||||
MD5 = "MD5"
|
||||
|
|
|
@ -8,7 +8,7 @@ You can profile any of your pages as follows::
|
|||
from cherrypy.lib import profiler
|
||||
|
||||
class Root:
|
||||
p = profile.Profiler("/path/to/profile/dir")
|
||||
p = profiler.Profiler("/path/to/profile/dir")
|
||||
|
||||
def index(self):
|
||||
self.p.run(self._index)
|
||||
|
|
|
@ -281,13 +281,14 @@ class _Builder2:
|
|||
# Everything else becomes args
|
||||
else :
|
||||
args.append(self.build(child))
|
||||
|
||||
return callee(*args, **kwargs)
|
||||
|
||||
def build_Keyword(self, o):
|
||||
key, value_obj = o.getChildren()
|
||||
value = self.build(value_obj)
|
||||
kw_dict = {key: value}
|
||||
return kw_dict
|
||||
return kw_dict
|
||||
|
||||
def build_List(self, o):
|
||||
return map(self.build, o.getChildren())
|
||||
|
@ -377,7 +378,39 @@ class _Builder3:
|
|||
def build_Index(self, o):
|
||||
return self.build(o.value)
|
||||
|
||||
def _build_call35(self, o):
|
||||
"""
|
||||
Workaround for python 3.5 _ast.Call signature, docs found here
|
||||
https://greentreesnakes.readthedocs.org/en/latest/nodes.html
|
||||
"""
|
||||
import ast
|
||||
callee = self.build(o.func)
|
||||
args = []
|
||||
if o.args is not None:
|
||||
for a in o.args:
|
||||
if isinstance(a, ast.Starred):
|
||||
args.append(self.build(a.value))
|
||||
else:
|
||||
args.append(self.build(a))
|
||||
kwargs = {}
|
||||
for kw in o.keywords:
|
||||
if kw.arg is None: # double asterix `**`
|
||||
rst = self.build(kw.value)
|
||||
if not isinstance(rst, dict):
|
||||
raise TypeError("Invalid argument for call."
|
||||
"Must be a mapping object.")
|
||||
# give preference to the keys set directly from arg=value
|
||||
for k, v in rst.items():
|
||||
if k not in kwargs:
|
||||
kwargs[k] = v
|
||||
else: # defined on the call as: arg=value
|
||||
kwargs[kw.arg] = self.build(kw.value)
|
||||
return callee(*args, **kwargs)
|
||||
|
||||
def build_Call(self, o):
|
||||
if sys.version_info >= (3, 5):
|
||||
return self._build_call35(o)
|
||||
|
||||
callee = self.build(o.func)
|
||||
|
||||
if o.args is None:
|
||||
|
@ -388,13 +421,16 @@ class _Builder3:
|
|||
if o.starargs is None:
|
||||
starargs = ()
|
||||
else:
|
||||
starargs = self.build(o.starargs)
|
||||
starargs = tuple(self.build(o.starargs))
|
||||
|
||||
if o.kwargs is None:
|
||||
kwargs = {}
|
||||
else:
|
||||
kwargs = self.build(o.kwargs)
|
||||
|
||||
if o.keywords is not None: # direct a=b keywords
|
||||
for kw in o.keywords:
|
||||
# preference because is a direct keyword against **kwargs
|
||||
kwargs[kw.arg] = self.build(kw.value)
|
||||
return callee(*(args + starargs), **kwargs)
|
||||
|
||||
def build_List(self, o):
|
||||
|
|
|
@ -49,7 +49,10 @@ def serve_file(path, content_type=None, disposition=None, name=None,
|
|||
|
||||
try:
|
||||
st = os.stat(path)
|
||||
except OSError:
|
||||
except (OSError, TypeError, ValueError):
|
||||
# OSError when file fails to stat
|
||||
# TypeError on Python 2 when there's a null byte
|
||||
# ValueError on Python 3 when there's a null byte
|
||||
if debug:
|
||||
cherrypy.log('os.stat(%r) failed' % path, 'TOOLS.STATIC')
|
||||
raise cherrypy.NotFound()
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue