Charles は Flashアプリケーションを作っていた開発者が、アプリケーションから利用するHTTP通信のデバッグを行うために作ったプロキシーです。
参考:
Flashにとどまらず、ブラウザやiOS, Android端末にCharlesで用意したプロキシーサーバーを設定することで、アプリケーションがAPIとどのような通信を行っているか確認したり、APIのレスポンスを書き換えてアプリケーションの挙動を確認したりすることが出来ます。
MacやiOSでCharlesプロキシを利用するのは、Charlesの標準機能で支援されていますが、Androidは手動でやらなくてはならなかったのでその手順のメモです。
環境は macOS High Sierra, Android 8.1 Emulator です。
Charles でプロキシーを有効にする
Charles でプロキシーを起動する。 ( Proxy
> Proxy Settings...
)
Emulatorに設定すべきプロキシの情報、Certificate取得用のURLを確認する。 ( Help
> SSL Proxying
> Install Chales Root Certificate on a Mobile Device or Remote Browser
)
Emulatorをプロキシーを有効にして起動する
上記で最後に確認した情報をもとに、コマンドラインから -http-proxy http://IP:PORT
を渡してEmulatorを起動するとプロキシーが有効になる。
niwatako の部分は適宜自身のユーザー名に読み替えてください。
niwatako$ /Users/niwatako/Library/Android/sdk/emulator/emulator -netdelay none -netspeed full -avd Nexus_S_API_27 -http-proxy http://172.21.21.204:8888
ちなみに -avd
のあとに渡す Android Virtual Deviceの名前 (上記では Nexus_S_API_27
) は、Android Studio のDevice Managerから確認できる。
あるいは
niwatako$ /Users/niwatako/Library/Android/sdk/emulator/emulator -list-avds
でavdを一覧できる。
Emulatorで実際に通信しようとするとCharles側にProxyとの接続を許可するかどうか問うダイアログが出るので、 Allow
する。
http
でプロキシを使いたいだけならこれで完了。
※ 追記: GUIからも設定できるんですね Using the emulator with a proxy
https で Charles Proxy を利用するようにする
https
でもプロキシを使いたければ、まず Charles でSSLプロキシーを有効にする ( Proxy
> SSL Proxying Settings
)。
Enable SSL Proxying
にチェックを入れ、Addから対象にしたい条件を追加。とりあえず全部有効にしたければ Host: *
, Port: *
にする。
この状態で https://
の適当なサイトに接続すると、証明書のエラーが出る。サイトの正規の証明書を使ってCharlesが通信し、CharlesとEmulatorはCharlesが用意した証明書で通信しようとしている。デバイスはCharlesの証明書を信用して良いものと製造時に教わっていないので、エラーが出る状態。
この状態でEmulatorのブラウザから Help
> SSL Proxying
> Install Chales Root Certificate on a Mobile Device or Remote Browser
で確認した chls.pro/ssl にアクセスしてCharlesのCertificateをダウンロードして、インストールさせる(信頼してよいものと覚えさせる)。
※もしもダウンロード出来ない場合(SDカードがないからダウンロード出来ません、という端末のEmulatorがあった)、Charlesの Help
> SSL Proxying
> Save Charles Root Certificate...
からCertificateをファイルとして保存し(拡張子をcerにしておくのが良いらしい)て、EmulatorにドラッグアンドドロップするとEmulator内のFilesアプリから開けるようになりました。
Credential Useは VPN and apps に設定すれば良い
Certificate をインストールして利用するには、AndroidデバイスにPINまたはパスコードによるロックをかける必要がある様子で、Certificateインストール時に設定を求められる。
デバイスに指紋認証はないので Continue without fingerprint で設定する
今回は適当なPINを設定してみました
ロック中に受信した通知をどうするか。開発時は全部見えてほしいので Show allを選択しました。
httpsで接続したGoogleとの通信がCharlesから覗けるようになりました。
困っていること
ダウンロードサイズが大きい時、 ERR_INCOMPLETE_CHUNKED_ENCODING が起きてCharlesとデバイス間でデータの受け渡しが失敗する様子。
Charlesのプロキシサーバーが原因だろうか。以下参考にNginxの場合の記事。
記事で紹介されているNginxで言うところの proxy_buffering みたいな設定をさわれる箇所がCharlesの設定には見当たらない。