Android Emulator のネットワークを設定する

エミュレータは、汎用性の高いネットワーク機能を備えています。これを使用して、アプリの複雑なモデリング環境やテスト環境をセットアップできます。このページでは、エミュレータのネットワーク アーキテクチャと機能について説明します。

ネットワーク アドレス空間

エミュレータの各インスタンスは、仮想ルーターまたはファイアウォール サービスの背後で実行されます。これにより、各インスタンスは開発マシンのネットワークのインターフェースと設定や、インターネットから分離されます。エミュレートしたデバイスでは、開発マシンやネットワーク上のその他のエミュレータ インスタンスは検出されず、イーサネット経由でルーターまたはファイアウォールに接続されていることだけが検出されます。

各インスタンスの仮想ルーターは、10.0.2/24 ネットワーク アドレス空間を管理します。ルーターによって管理されるアドレスはすべて、10.0.2.xx の形式です(xx は数字)。この空間内のアドレスは、エミュレータまたはルーターによって次のように事前に割り当てられます。

ネットワーク アドレス 説明
10.0.2.1 ルーターまたはゲートウェイ アドレス
10.0.2.2 ホスト ループバック インターフェースへの特殊エイリアス(開発マシンの 127.0.0.1)
10.0.2.3 1 番目の DNS サーバー
10.0.2.4 / 10.0.2.5 / 10.0.2.6 オプションの 2 番目、3 番目、4 番目の DNS サーバー
10.0.2.15 エミュレートしたデバイス ネットワーク(イーサネットで接続した場合)
10.0.2.16 Wi-Fi で接続した場合のエミュレートされたデバイス ネットワーク
127.0.0.1 エミュレートしたデバイスのループバック インターフェース

実行中のすべてのエミュレータ インスタンスで同じアドレス割り当てが使用されます。つまり、マシン上で 2 つのインスタンスを同時に実行している場合、それぞれに固有のルーターがあり、その背後でそれぞれ 10.0.2.15 の IP アドレスが割り当てられています。2 つのインスタンスはルーターによって分離されており、同じネットワーク上で相互に検出することはできません。エミュレータ インスタンスを TCP/UDP で通信できるようにする方法については、エミュレータ インスタンスを相互接続するのセクションをご覧ください。

開発マシンのアドレス 127.0.0.1 は、エミュレータのループバック インターフェースに対応します。開発マシンのループバック インターフェースで実行されているサービスにアクセスするには、代わりに特殊アドレス 10.0.2.2 を使用します。

エミュレートしたデバイスの事前割り当てアドレスは、Android Emulator に固有であり、特にルーターまたはファイアウォールの背後でネットワーク アドレス変換される可能性もある実際のデバイスでは、大きく異なる可能性があります。

ローカル ネットワークの制限

エミュレータで実行されている Android アプリは、ワークステーションで利用可能なネットワークに接続できます。ただし、アプリはハードウェアに直接接続するのではなく、エミュレータを介して接続し、エミュレータはワークステーション上で通常のアプリのように動作します。これにより、いくつかの制限が生じる可能性があります。

  • エミュレートしたデバイスとの通信は、マシンで実行されているファイアウォール プログラムによってブロックされる場合があります。
  • エミュレートしたデバイスとの通信は、マシンが接続されている別の(物理)ファイアウォールまたはルーターによってブロックされる場合があります。

エミュレータの仮想ルーターは、エミュレートしたデバイスに代わってすべてのアウトバウンド TCP / UDP 接続とメッセージを処理できる必要があります(開発マシンのネットワーク環境で許可されている場合)。ホスト オペレーティング システムとネットワークによる制限を除き、ポート番号やポート範囲には初めから設けられている制限はありません。

環境によっては、エミュレータが他のプロトコル(「ping」に使用される ICMP など)をサポートできない場合があります。現在、エミュレータは IGMP(マルチキャスト)をサポートしていません。

ネットワーク リダイレクトを使用する

仮想ルーターの背後にあるエミュレータ インスタンスと通信するには、仮想ルーターでネットワーク リダイレクトをセットアップします。するとクライアントは仮想ルーター上の指定されたゲストポートに接続できるようになり、仮想ルーターはゲストポートとエミュレートしたデバイスのホストポートの間でトラフィックを転送します。

ネットワーク リダイレクトをセットアップするには、エミュレータ インスタンスでホストとゲストのポートとアドレスのマッピングを作成します。以降のセクションで説明するように、ネットワーク リダイレクトをセットアップする方法は 2 つあります。エミュレータ コンソール コマンドを使用する方法と、Android Debug Bridge(adb)ツールを使用する方法です。

エミュレータ コンソールでリダイレクトをセットアップする

各エミュレータ インスタンスには制御コンソールが用意されており、これに接続して各インスタンスに固有のコマンドを発行できます。redir コンソール コマンドを使用して、エミュレータ インスタンスでの必要性に応じてリダイレクトをセットアップします。

最初に、ターゲットのエミュレータ インスタンスのコンソール ポート番号を特定します。たとえば、最初に起動したエミュレータ インスタンスのコンソールのポート番号が 5554 だとします。次に、以下のようにコンソール ポート番号を指定して、ターゲットのエミュレータ インスタンスのコンソールに接続します。

telnet localhost 5554

接続したら、リダイレクトをセットアップする前に認証を行う必要があります。その方法について詳しくは、コンソール セッションを開始、停止するをご覧ください。認証したら、redir コマンドを使用してリダイレクトを操作します。

リダイレクトを追加するには、次のようなコマンドを使用します。

redir add <protocol>:<host-port>:<guest-port>

ここで、<protocol>tcp または udp です。<host-port><guest-port> は、マシンとエミュレートしたシステムの間のマッピングを設定します。

たとえば、次のコマンドは、127.0.0.1:5000 のホスト(開発)マシンへのすべての着信 TCP 接続を処理するリダイレクトをセットアップし、10.0.2.15:6000 のエミュレートしたシステムに渡します。

redir add tcp:5000:6000

リダイレクトを削除するには、redir del コマンドを使用します。特定のインスタンスのすべてのリダイレクトを一覧表示するには、redir list を使用します。こうしたコンソール コマンドの詳細については、エミュレータ コンソール コマンドを送信するをご覧ください。

なお、ポート番号はローカル環境によって制限されます。通常、特別な管理者権限がないと 1024 未満のホストポート番号を使用できません。また、マシン上の別のプロセスですでに使用されているホストポートに対してリダイレクトを設定することはできません。設定した場合、redir はその旨を示すエラー メッセージを生成します。

adb でリダイレクトをセットアップする

Android Debug Bridge(adb)ツールは、ポート転送の機能を提供します。これにより、上記の方法とは別の方法でネットワーク リダイレクトをセットアップできます。詳細については、adb のドキュメントのポート転送をセットアップするをご覧ください。

なお、現在のところ adb には adb サーバーを停止する以外にリダイレクトを削除する方法がありません。

エミュレータの DNS 設定を構成する

エミュレータは起動時にシステムが現在使用している DNS サーバーのリストを読み取ります。次に、このリストにある最大 4 台のサーバーの IP アドレスを保存し、必要に応じて、エミュレートしたアドレス 10.0.2.3、10.0.2.4、10.0.2.5、10.0.2.6 でエイリアスをセットアップします。

Linux と macOS の場合、エミュレータは /etc/resolv.conf ファイルを解析して DNS サーバーのアドレスを取得します。Windows の場合は、GetNetworkParams() API を呼び出してアドレスを取得します。このプロセスでは通常、エミュレータが「hosts」ファイル(Linux / macOS では /etc/hosts、Windows では %WINDOWS%/system32/HOSTS)の内容を無視する点に注意する必要があります。

エミュレータをコマンドラインで起動する場合、-dns-server <serverList> オプションを使用して、使用する DNS サーバーのアドレスを手動で指定できます。ここで <serverList> は、サーバー名または IP アドレスのカンマ区切りのリストです。エミュレートしたネットワークで DNS 解決の問題(ウェブブラウザ使用時に表示される「不明なホストエラー」メッセージなど)が発生した場合、このオプションが役立つことがあります。

エミュレータでプロキシを使用する

多くの企業ネットワークでは、インターネットへの直接接続はネットワーク管理者によって拒否されています。代わりに、インターネット接続は特定のプロキシを経由する必要があります。プロキシが必要なネットワークでインターネットにアクセスするには、エミュレータはプロキシが存在することと、プロキシに接続する必要があることを認識する必要があります。

HTTP の性質により、ウェブサーバーへの直接接続とプロキシ経由の接続では、異なる GET リクエストが生成されます。エミュレータはプロキシと通信する前に、仮想デバイスからの GET リクエストを透過的に書き換えて、動作するようにします。

エミュレータがプロキシ サーバー経由でインターネットにアクセスする必要がある場合は、エミュレータの [Extended controls] 画面からカスタム HTTP プロキシを構成できます。

  1. エミュレータを開いた状態で、その他アイコン をクリックします。
  2. [Settings] > [Proxy] をクリックします。
  3. HTTP プロキシ設定を定義します。

あるいは、エミュレータの起動時に -http-proxy <proxy> オプションを使用してコマンドラインからプロキシを構成できます。この場合、プロキシ情報を <proxy> で指定します。形式は次のいずれかです。

http://<machineName>:<port>

または

http://<username>:<password>@<machineName>:<port>

-http-proxy オプションは、すべての発信 TCP 接続に対して、指定された HTTP または HTTPS プロキシを使用するようにエミュレータに強制します。UDP のリダイレクトはサポートされていません。

環境変数 http_proxy を、<proxy> に使用する値に定義することもできます。この場合、-http-proxy コマンドで <proxy> の値を指定する必要はありません。エミュレータは起動時に http_proxy 環境変数の値をチェックし、定義されている場合は自動的にその値を使用します。

-debug-proxy オプションを使用することで、プロキシ接続の問題を診断できます。

エミュレータ インスタンスを相互接続する

あるエミュレータ インスタンスを別のエミュレータ インスタンスと通信できるようにするには、以下のとおりネットワーク リダイレクトをセットアップします。

次のような環境だとします。

  • A は開発マシンです。
  • B は、A で実行される最初のエミュレータ インスタンスです。
  • C は 2 番目のエミュレータ インスタンスであり、これも A で実行されます。

B でサーバーを動作させ、C がそのサーバーに接続する場合は、次のようにセットアップします。

  1. 10.0.2.15:<serverPort> をリッスンするように B のサーバーをセットアップします。
  2. B のコンソールで、A:localhost:<localPort> から B:10.0.2.15:<serverPort> へのリダイレクトを設定します。
  3. C で、クライアントを 10.0.2.2:<localPort> に接続します。

たとえば、HTTP サーバーを実行する場合は、<serverPort> を 80 にし、<localPort> を 8080 にします。

  • B は 10.0.2.15:80 でリッスンします。
  • B のコンソールで、redir add tcp:8080:80. を発行します。
  • C が 10.0.2.2:8080 に接続します。

別のエミュレータ インスタンスに音声通話または SMS を送信する

エミュレータは、シミュレートされた音声通話と SMS メッセージを、あるインスタンスから別のインスタンスに自動的に転送します。音声通話または SMS を送信するには、いずれかのエミュレータから電話アプリまたは SMS アプリをそれぞれ使用します。

シミュレートされた音声通話を別のエミュレータ インスタンスに対して発信するには:

  1. 発信側のエミュレータ インスタンスで電話アプリを起動します。
  2. ダイヤルする番号として、ターゲットのインスタンスのコンソール ポート番号を入力します。

    ターゲットのインスタンスのコンソール ポート番号は、別のウィンドウで実行されている場合はそのウィンドウのタイトルを確認することで判断できますが、ツール ウィンドウで実行されている場合は判断できません。コンソール ポート番号は「Android Emulator (<port>)」として表示されます。

    adb devices コマンドで、実行中の仮想デバイスとそのコンソール ポート番号のリストを出力することもできます。詳細については、デバイスのクエリを行うをご覧ください。

  3. ダイヤルボタンをクリックします。ターゲットのエミュレータ インスタンスに新しい着信が表示されます。

SMS メッセージを別のエミュレータ インスタンスに送信するには:

  1. SMS アプリを起動します(利用可能な場合)。
  2. ターゲットのエミュレータ インスタンスのコンソール ポート番号を SMS アドレスとして指定します。
  3. メッセージ テキストを入力します。
  4. メッセージを送信します。メッセージはターゲットのエミュレータ インスタンスに配信されます。
  5. エミュレータ コンソールに接続して、音声通話や SMS の着信をシミュレートすることもできます。詳しくは、電話のエミュレーションSMS のエミュレーションをご覧ください。