mirror of
https://github.com/Grasscutters/mitmproxy.git
synced 2024-11-27 02:24:18 +00:00
Make Message classes more self-contained.
This commit is contained in:
parent
b2deb470de
commit
a09584b9e6
@ -85,6 +85,7 @@ def serve(msg, fp, settings, request_host=None):
|
||||
|
||||
Calling this function may modify the object.
|
||||
"""
|
||||
msg = msg.resolve(settings, request_host)
|
||||
started = time.time()
|
||||
|
||||
hdrs = msg.headervals(settings, request_host)
|
||||
@ -96,7 +97,11 @@ def serve(msg, fp, settings, request_host=None):
|
||||
if msg.body:
|
||||
vals.append(msg.body.value.get_generator(settings))
|
||||
vals.reverse()
|
||||
actions = msg.ready_actions(settings, request_host)
|
||||
|
||||
actions = msg.actions[:]
|
||||
actions.sort()
|
||||
actions.reverse()
|
||||
actions = [i.intermediate(settings) for i in actions]
|
||||
|
||||
disconnect = write_values(fp, vals, actions[:])
|
||||
duration = time.time() - started
|
||||
@ -105,18 +110,7 @@ def serve(msg, fp, settings, request_host=None):
|
||||
started = started,
|
||||
duration = duration,
|
||||
)
|
||||
for i in msg.logattrs:
|
||||
v = getattr(msg, i)
|
||||
# Careful not to log any VALUE specs without sanitizing them first. We truncate at 1k.
|
||||
if hasattr(v, "values"):
|
||||
v = [x[:TRUNCATE] for x in v.values(settings)]
|
||||
v = "".join(v).encode("string_escape")
|
||||
elif hasattr(v, "__len__"):
|
||||
v = v[:TRUNCATE]
|
||||
v = v.encode("string_escape")
|
||||
ret[i] = v
|
||||
ret["spec"] = msg.spec()
|
||||
ret.update(msg.logflags)
|
||||
ret.update(msg.log(settings))
|
||||
return ret
|
||||
|
||||
|
||||
@ -228,7 +222,7 @@ class _Token(object):
|
||||
"""
|
||||
return None
|
||||
|
||||
def resolve(self, msg): # pragma: no cover
|
||||
def resolve(self, msg, settings, request_host): # pragma: no cover
|
||||
"""
|
||||
Resolves this token to ready it for transmission. This means that
|
||||
the calculated offsets of actions are fixed.
|
||||
@ -559,7 +553,7 @@ class _Action(_Token):
|
||||
def __init__(self, offset):
|
||||
self.offset = offset
|
||||
|
||||
def resolve_offset(self, msg, settings, request_host):
|
||||
def resolve(self, msg, settings, request_host):
|
||||
"""
|
||||
Resolves offset specifications to a numeric offset. Returns a copy
|
||||
of the action object.
|
||||
@ -713,11 +707,11 @@ class _Message(object):
|
||||
l += len(i.value.get_generator(settings))
|
||||
return l
|
||||
|
||||
def headervals(self, settings, request_host):
|
||||
hdrs = self.headers[:]
|
||||
def resolve(self, settings, request_host):
|
||||
tokens = self.tokens[:]
|
||||
if not self.raw:
|
||||
if self.body and not utils.get_header("Content-Length", self.headers):
|
||||
hdrs.append(
|
||||
tokens.append(
|
||||
Header(
|
||||
ValueLiteral("Content-Length"),
|
||||
ValueLiteral(str(len(self.body.value.get_generator(settings)))),
|
||||
@ -725,7 +719,7 @@ class _Message(object):
|
||||
)
|
||||
if request_host:
|
||||
if not utils.get_header("Host", self.headers):
|
||||
hdrs.append(
|
||||
tokens.append(
|
||||
Header(
|
||||
ValueLiteral("Host"),
|
||||
ValueLiteral(request_host)
|
||||
@ -733,23 +727,21 @@ class _Message(object):
|
||||
)
|
||||
else:
|
||||
if not utils.get_header("Date", self.headers):
|
||||
hdrs.append(
|
||||
tokens.append(
|
||||
Header(
|
||||
ValueLiteral("Date"),
|
||||
ValueLiteral(formatdate(timeval=None, localtime=False, usegmt=True))
|
||||
)
|
||||
)
|
||||
intermediate = self.__class__(tokens)
|
||||
return self.__class__([i.resolve(intermediate, settings, request_host) for i in tokens])
|
||||
|
||||
def headervals(self, settings, request_host):
|
||||
values = []
|
||||
for h in hdrs:
|
||||
for h in self.headers:
|
||||
values.extend(h.values(settings))
|
||||
return values
|
||||
|
||||
def ready_actions(self, settings, request_host):
|
||||
actions = [i.resolve_offset(self, settings, request_host) for i in self.actions]
|
||||
actions.sort()
|
||||
actions.reverse()
|
||||
return [i.intermediate(settings) for i in actions]
|
||||
|
||||
@abc.abstractmethod
|
||||
def preamble(self, settings): # pragma: no cover
|
||||
pass
|
||||
@ -758,6 +750,24 @@ class _Message(object):
|
||||
def expr(klass): # pragma: no cover
|
||||
pass
|
||||
|
||||
def log(self, settings):
|
||||
"""
|
||||
A dictionary that should be logged if this message is served.
|
||||
"""
|
||||
ret = {}
|
||||
for i in self.logattrs:
|
||||
v = getattr(self, i)
|
||||
# Careful not to log any VALUE specs without sanitizing them first. We truncate at 1k.
|
||||
if hasattr(v, "values"):
|
||||
v = [x[:TRUNCATE] for x in v.values(settings)]
|
||||
v = "".join(v).encode("string_escape")
|
||||
elif hasattr(v, "__len__"):
|
||||
v = v[:TRUNCATE]
|
||||
v = v.encode("string_escape")
|
||||
ret[i] = v
|
||||
ret["spec"] = self.spec()
|
||||
return ret
|
||||
|
||||
|
||||
Sep = pp.Optional(pp.Literal(":")).suppress()
|
||||
|
||||
@ -774,7 +784,6 @@ class Response(_Message):
|
||||
Reason
|
||||
)
|
||||
logattrs = ["code", "reason", "version", "body"]
|
||||
logflags = dict()
|
||||
@property
|
||||
def code(self):
|
||||
return self._get_token(Code)
|
||||
@ -820,7 +829,6 @@ class Request(_Message):
|
||||
Raw
|
||||
)
|
||||
logattrs = ["method", "path", "body"]
|
||||
logflags = dict()
|
||||
@property
|
||||
def method(self):
|
||||
return self._get_token(Method)
|
||||
@ -855,16 +863,14 @@ class Request(_Message):
|
||||
return ":".join([i.spec() for i in self.tokens])
|
||||
|
||||
|
||||
class PathodErrorResponse(Response):
|
||||
logflags = dict(internal=True)
|
||||
def __init__(self, reason, body=None):
|
||||
def PathodErrorResponse(reason, body=None):
|
||||
tokens = [
|
||||
Code("800"),
|
||||
Header(ValueLiteral("Content-Type"), ValueLiteral("text/plain")),
|
||||
Reason(ValueLiteral(reason)),
|
||||
Body(ValueLiteral("pathod error: " + (body or reason))),
|
||||
]
|
||||
Response.__init__(self, tokens)
|
||||
return Response(tokens)
|
||||
|
||||
|
||||
FILESTART = "+"
|
||||
|
@ -257,10 +257,10 @@ class Test_Action:
|
||||
l.sort()
|
||||
assert l[0].offset == 0
|
||||
|
||||
def test_resolve_offset(self):
|
||||
def test_resolve(self):
|
||||
r = language.parse_request({}, 'GET:"/foo"')
|
||||
e = language.DisconnectAt("r")
|
||||
ret = e.resolve_offset(r, {}, None)
|
||||
ret = e.resolve(r, {}, None)
|
||||
assert isinstance(ret.offset, int)
|
||||
|
||||
def test_repr(self):
|
||||
@ -584,9 +584,9 @@ class TestResponse:
|
||||
s = cStringIO.StringIO()
|
||||
language.serve(x, s, {})
|
||||
assert x.length({}, None) == len(s.getvalue())
|
||||
testlen(language.parse_response({}, "400:m'msg'"))
|
||||
testlen(language.parse_response({}, "400:m'msg':h'foo'='bar'"))
|
||||
testlen(language.parse_response({}, "400:m'msg':h'foo'='bar':b@100b"))
|
||||
testlen(language.parse_response({}, "400:m'msg':r"))
|
||||
testlen(language.parse_response({}, "400:m'msg':h'foo'='bar':r"))
|
||||
testlen(language.parse_response({}, "400:m'msg':h'foo'='bar':b@100b:r"))
|
||||
|
||||
def test_maximum_length(self):
|
||||
def testlen(x):
|
||||
|
Loading…
Reference in New Issue
Block a user