Firm up reverse proxy specification.

- Extract proxy spec parsing and unparsing functions.
- Add a status indicator in mitmproxy.
- Add the "R" keybinding for changing the reverse proxy from within mitmproxy.
This commit is contained in:
Aldo Cortesi 2012-02-18 16:27:09 +13:00
parent a7df6e1503
commit 6ad8b1a15d
6 changed files with 59 additions and 17 deletions

View File

@ -67,7 +67,7 @@ def common_options(parser):
parser.add_option(
"-R",
action="store", dest="reverse_proxy", default=None,
help="Reverse proxy: upstream server host:port"
help="Reverse proxy to upstream server: http[s]://host[:port]"
)
parser.add_option(
"-q",

View File

@ -122,28 +122,32 @@ class StatusBar(common.WWrap):
if self.master.client_playback:
r.append("[")
r.append(("statusbar_highlight", "cplayback"))
r.append(("key", "cplayback"))
r.append(":%s to go]"%self.master.client_playback.count())
if self.master.server_playback:
r.append("[")
r.append(("statusbar_highlight", "splayback"))
r.append(("key", "splayback"))
r.append(":%s to go]"%self.master.server_playback.count())
if self.master.state.intercept_txt:
r.append("[")
r.append(("statusbar_highlight", "i"))
r.append(("key", "i"))
r.append(":%s]"%self.master.state.intercept_txt)
if self.master.state.limit_txt:
r.append("[")
r.append(("statusbar_highlight", "l"))
r.append(("key", "l"))
r.append(":%s]"%self.master.state.limit_txt)
if self.master.stickycookie_txt:
r.append("[")
r.append(("statusbar_highlight", "t"))
r.append(("key", "t"))
r.append(":%s]"%self.master.stickycookie_txt)
if self.master.stickyauth_txt:
r.append("[")
r.append(("statusbar_highlight", "u"))
r.append(("key", "u"))
r.append(":%s]"%self.master.stickyauth_txt)
if self.master.server.config.reverse_proxy:
r.append("[")
r.append(("key", "R"))
r.append(":%s]"%utils.unparse_url(*self.master.server.config.reverse_proxy))
opts = []
if self.master.anticache:
@ -667,6 +671,12 @@ class ConsoleMaster(flow.FlowMaster):
def set_intercept(self, txt):
return self.state.set_intercept(txt)
def set_reverse_proxy(self, txt):
s = utils.parse_proxy_spec(txt)
if not s:
return "Invalid reverse proxy specification"
self.server.config.reverse_proxy = s
def changeview(self, v):
if v == "r":
self.state.view_body_mode = common.VIEW_BODY_RAW
@ -754,6 +764,17 @@ class ConsoleMaster(flow.FlowMaster):
),
self.quit,
)
elif k == "R":
if self.server.config.reverse_proxy:
p = utils.unparse_url(*self.server.config.reverse_proxy)
else:
p = ""
self.prompt(
"Reverse proxy: ",
p,
self.set_reverse_proxy
)
self.sync_list_view()
elif k == "s":
if self.script:
self.load_script(None)

View File

@ -212,8 +212,10 @@ class FUrl(_Rex):
def __call__(self, o):
if isinstance(o, flow.Response):
c = o.request
else:
elif isinstance(o, flow.Request):
c = o
else:
return False
return re.search(self.expr, c.get_url())

View File

@ -303,13 +303,6 @@ class Request(HTTPMsg):
c.headers = self.headers.copy()
return c
def _hostport(self):
if (self.port, self.scheme) in [(80, "http"), (443, "https")]:
host = self.host
else:
host = "%s:%s"%(self.host, self.port)
return host
def get_form_urlencoded(self):
"""
Retrieves the URL-encoded form data, returning a list of (key,
@ -352,7 +345,7 @@ class Request(HTTPMsg):
"""
Returns a URL string, constructed from the Request's URL compnents.
"""
return "%s://%s%s"%(self.scheme, self._hostport(), self.path)
return utils.unparse_url(self.scheme, self.host, self.port, self.path)
def set_url(self, url):
"""
@ -387,7 +380,7 @@ class Request(HTTPMsg):
]
)
if not 'host' in headers:
headers["host"] = [self._hostport()]
headers["host"] = [utils.hostport(self.scheme, self.host, self.port)]
content = self.content
if content is None:
content = ""

View File

@ -427,6 +427,23 @@ def parse_proxy_spec(url):
return p[:3]
def hostport(scheme, host, port):
"""
Returns the host component, with a port specifcation if needed.
"""
if (port, scheme) in [(80, "http"), (443, "https")]:
return host
else:
return "%s:%s"%(host, port)
def unparse_url(scheme, host, port, path=""):
"""
Returns a URL string, constructed from the specified compnents.
"""
return "%s://%s%s"%(scheme, hostport(scheme, host, port), path)
def clean_hanging_newline(t):
"""
Many editors will silently add a newline to the final line of a

View File

@ -208,6 +208,14 @@ class u_parse_proxy_spec(libpry.AutoTree):
assert not utils.parse_proxy_spec("foo.com")
class u_unparse_url(libpry.AutoTree):
def test_simple(self):
assert utils.unparse_url("http", "foo.com", 99, "") == "http://foo.com:99"
assert utils.unparse_url("http", "foo.com", 80, "") == "http://foo.com"
assert utils.unparse_url("https", "foo.com", 80, "") == "https://foo.com:80"
assert utils.unparse_url("https", "foo.com", 443, "") == "https://foo.com"
class u_parse_url(libpry.AutoTree):
def test_simple(self):
assert not utils.parse_url("")
@ -262,6 +270,7 @@ tests = [
uLRUCache(),
u_parse_url(),
u_parse_proxy_spec(),
u_unparse_url(),
u_parse_size(),
uclean_hanging_newline()
]