Spica*

プログラミングの話。

mitmproxyを使ってresponse body書換え

ふと思いついてmitmproxyを触ってみてた。今まであんまりちゃんとmitmproxyのhookできたことがなくて、ちゃんと調べてみてたんだけど、ちょっとクセがあるっぽい感じだった。

  • mitmproxyではpythonスクリプトを間に差し込み、リクエストを書き換えたりできる
  • mitmproxy -s my_script.py みたいな感じで起動すると、指定したスクリプトでリクエスト・レスポンスを書き換えることが出来る。
    • mitmdump -s my_script.py でもいける。こちらの場合、標準出力に表示されるので、スクリプトに問題があった時よく分かる
    • mitmproxy -s my_script.py での起動の場合、スクリプトエラーがあると、読まれないっぽい。エラーも出ない
    • スクリプトエラーがあると、左下の表記がちょっと違う
      • エラーあり: f:id:esperia:20160405011037p:plain:h35
      • エラーなし: f:id:esperia:20160405011044p:plain:h37
    • 引数をmy_script.pyに渡す場合は、 mitmdump -s 'my_script.py --foo 42' のように渡す

上記を踏まえて。

下記のようにスクリプトを書いた。このスクリプトは先程の Inline scripts の部分を元に書いた。

from libmproxy.models import decoded

def start(context, argv):
    f = open('test.json')
    context.mydata = f.read()
    f.close()
    print(context.mydata)

def response(context, flow):
    with decoded(flow.response):
        original = "example.com"
        target_path = '/path/to/get'
        print("handle request: %s %s" % (flow.request.host, flow.request.path))
        print("  Host: %s" % (flow.request.headers["Host"]))

        if original in flow.request.headers["Host"]:
            if flow.request.path == target_path:
                print("Match request.")
                flow.response.content = context.mydata

上記を mitmdump -T --host -s my_scripts.py で起動。うまく書き換わった。 もっと細かくプログラム組めば、オレオレセッション値とか設定できそう。

まれにデバッグとか調査とかで使うことがあるので慣れておきたいな。