Skip to content

Instantly share code, notes, and snippets.

@muellermartin
Created January 25, 2020 15:44
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save muellermartin/3c2135a05b9baf10cec4e20d21839bdc to your computer and use it in GitHub Desktop.
Save muellermartin/3c2135a05b9baf10cec4e20d21839bdc to your computer and use it in GitHub Desktop.
Script for mitmproxy to replace response bodies with the content of arbitrary other files
"""
This script replaces a response body with the contents of a specific file.
"""
import mimetypes
import os
import typing
from mitmproxy import ctx
from mitmproxy import exceptions
from mitmproxy import flowfilter
from mitmproxy import http
from mitmproxy import optmanager
class ReplaceFiles:
def __init__(self):
mimetypes.init()
self.lst = []
def load(self, loader: optmanager.OptManager) -> None:
loader.add_option(
name="replacefiles",
typespec=typing.Sequence[str],
default=[],
help="""Replacements of files of the form
[filter expression]:[path to file]
"""
)
def configure(self, updated):
if "replacefiles" in updated:
lst = []
for rep in ctx.options.replacefiles:
fpatt, filename = rep.split(":", 1)
filename = os.path.expanduser(filename)
flt = flowfilter.parse(fpatt)
if not flt:
raise exceptions.OptionsError(
"Invalid filter pattern: %s" % fpatt
)
if not os.path.isfile(filename):
raise exceptions.OptionsError(
"Invalid file path: {}".format(filename)
)
lst.append((flt, filename))
self.lst = lst
def response(self, flow: http.HTTPFlow) -> None:
for flt, filename in self.lst:
if flt(flow):
try:
with open(filename, "rb") as f:
c = f.read()
except IOError:
ctx.log.warn(
"Could not read replacement file {}".format(filename)
)
return
flow.response.status_code = 200
flow.response.reason = "OK"
ctype, enc = mimetypes.guess_type(filename, strict=False)
if ctype is not None:
flow.response.headers["Content-Type"] = ctype
if enc is not None:
flow.response.headers["Content-Encoding"] = enc
elif "Content-Encoding" in flow.response.headers:
del(flow.response.headers["Content-Encoding"])
flow.response.content = c
addons = [ReplaceFiles()]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment