2014年11月29日土曜日

Androidのネットワーク通信に関するメモ

Androidのネットワーク通信


●パーミッション


□ネットワークの接続許可

<uses-permission android:name="android.permission.INTERNET" />

□ネットワークの接続状態を確認する

<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />

→ 接続不可能な場合のハンドリングに使用


●ネットワークの通信状態


ユースケース

・ネットワークに接続されていない場合は、ローカルにキャッシュされたデータを使用したい。
・ファイルサイズが大きい場合にwifiに接続時にのみダウンロードさせたい。

How


  • ContextからConnectivityManagerを取得する


ex)

public class MyActivity extends Activity {
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        // do something...
        // Context 経由でインスタンスを取得する ←★ContextがあればConnectivityManagerを取得可能
        ConnectivityManager cm = (ConnectivityManager) getSystemService(CONNECTIVITY_SERVICE);
        NetworkInfo info = cm.getActiveNetworkInfo();
        if (info.isConnected()) { ←★接続の確認
            Toast.makeText(this, info.getTypeName() + " connected", Toast.LENGTH_LONG).show();
        }
    }
}


●接続しているネットワークの種別


How


  • ConnectivityManagerからNetworkInfoを取得


ex)
ConnectivityManager cm = (ConnectivityManager) getSystemService(CONNECTIVITY_SERVICE);
NetworkInfo info = cm.getActiveNetworkInfo(); ←★ConnectivityManagerからNetworkInfoを取得
if (info.getType() == ConnectivityManager.TYPE_WIFI) {
    // wifi時のみ動作する処理を記述
}


●Http通信


Androidで用意されているライブラリ


  • HttpURLConnection:I/Oストリームを用いた通信の入出力処理を実装(Froyo以前ではコネクションプールの深刻なバグを含む)
  • Apache HttpClient:HttpURLConnectionより高いレイアの実装。抽象化された入出力を使うことができる(Froyo以前では使用が推奨される)



●非同期処理



  • ネットワーク通信の処理は、メインスレッド(UIスレッド)では実施しないこと。



●URLConnection:APIがシンプル、サイズが小さい



  1. URL#openConnection():接続の開始(レスポンスの型をHttpURLConnection型へキャスト)
  2. ヘッダーの設定
  3. HttpURLConnection#setDoOutput(true):bodyが存在する場合に明示する方法。接続の確率後に、getOutputStream()で取得したOutputStreamにbodyの内容を書き込む
  4. connect()で接続を確立する。setDoOutput(false)の場合、5にすすむ。setDoOutput(true)の場合、getOutputStreamで取得したOutputStreamに情報を書き込み、クローズするまでデータを送信する。closeを呼び出したら5にすすむ
  5. getResponseCode()でステータスコードを確認する
  6. getInputStream()でレスポンスを取得する



□ GET処理


ex)

URL url = new URL("http://mixi.jp");
HttpURLConnection connection = null;
try {
    connection = (HttpURLConnection) url.openConnection();
    connection.connect();
    InputStream is = connection.getInputStream();
    StringBuilder src = new StringBuilder();
    while (true) {
        byte[] line = new byte[1024];
        int size = is.read(line);
        if (size <= 0)
            break;
        src.append(new String(line, "euc-jp"));
    }
} catch (IOException e) {
    e.printStackTrace();
} finally{
    connection.disconnect();
}


□POST処理


ex)

URL url = new URL("http://mixi.jp");
HttpURLConnection connection = null;
try {
    connection = (HttpURLConnection) url.openConnection();
    connection.setRequestMethod("POST");
    connection.setDoOutput(true);
    String postData = "hoge=fuga&piyo=test";
    OutputStream os = connection.getOutputStream();
    os.write(postData.getBytes());
    os.flush();
    os.close();
    InputStream is = connection.getInputStream();
    StringBuilder src = new StringBuilder();
    while (true) {
        byte[] line = new byte[1024];
        int size = is.read(line);
        if (size <= 0)
            break;
        src.append(new String(line, "euc-jp"));
    }
} catch (IOException e) {
    e.printStackTrace();
} finally{
    connection.disconnect();
}


●ApacheHttpClient:Androidに組み込まれたライブラリはバージョンが古い、必要なら新しいものを別途組み込む


□GET処理

ex)

HttpClient client = new DefaultHttpClient();
try {
    client.execute(new HttpGet("http://mixi.jp"),
            new ResponseHandler<String>() {
                public String handleResponse(HttpResponse response)
                        throws ClientProtocolException, IOException {
                    return EntityUtils.toString(response.getEntity());
                }
            });
} catch (IOException e) {
    e.printStackTrace();
}

0 件のコメント:

コメントを投稿