AndroidでTwitter APIからパブリックタイムラインを見てみた

ただいま、「XML->ID、POST内容、時間をPOSTごとに分けて表示」と言う仕組みを作ろうとして詰まっております。取り合えず下記のソースの段階ではXMLそのまんまのテキストが見れるはず。

気付かなくてハマッた点

EclipeseにAndroidプラグインを入れているとAndroidアプリのプロジェクトを作れますが、これはそのままの状態だと、「プログラムに問題が無くても」通信機能が使えません。Twitter APIにアクセスするに当たってorg.apache.httpの辺りを使ったのがこの制限に引っかかったようです。

Manifest.xmlを開いて、

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

このように追記してやることで解決しました。
cf.Security and Permissions - Android

TwitterApi.java

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;

import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.HttpStatus;
import org.apache.http.StatusLine;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.DefaultHttpClient;

import android.util.Log;

public class TwitterApi {

	private HttpClient client = new DefaultHttpClient();
	
	//引数で受け取ったuriからGETしてレスポンスの本文部分を返す
	//cf.http://svn.apache.org/repos/asf/httpcomponents/httpclient/trunk/module-client/src/examples/org/apache/http/examples/client/ClientConnectionRelease.java
	public String Getter(String uri) 
	throws IllegalStateException, ClientProtocolException, IOException  {
		
		String answer = null;
		HttpGet method = new HttpGet(uri);
		StatusLine statusline;	//Status-Lineはレスポンスの最初の行
			
			
			//clientでGetを実行。レスポンスの中からStatusLineを取り出す
			//cf."6.1 Status-Line" http://www.ietf.org/rfc/rfc2616.txt
			HttpResponse response = client.execute(method);
			statusline = response.getStatusLine();
			
			//リクエストが成功
			if (statusline.getStatusCode() == HttpStatus.SC_OK ){
						
				HttpEntity httpentity = response.getEntity();
				BufferedReader reader = new BufferedReader(
						new InputStreamReader(httpentity.getContent()));
				
				//一行ずつstrbufへ追加
				String line;
				StringBuffer	strbuffer = new StringBuffer();
				try {
					while ((line = reader.readLine()) != null){
						strbuffer.append(line);
						Log.d("Kitwi", "copying line");
					}
				} catch (IOException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}finally{
					answer = strbuffer.toString();
					Log.d("Kitwi", "line copy done");
				
					//HTTP接続の「優雅な」解放も兼ねる
					try {
						reader.close();
					} catch (IOException e) {
						method.abort();
						e.printStackTrace();
					}
				}
			}
			else{
				answer = "サーバーエラー: "+statusline.toString();
			}
				
			return answer;
		}
			
	//引数を取らずにパブリックタイムラインをStringで返す
	public String getPublicTimeline() {
		TwitterApi		api	= new TwitterApi();
		String			uri	= "http://twitter.com/statuses/public_timeline.xml";
		String			tl = null;
		
		//公開TLの本文(XML部分)を返す		
		Log.d("Kitwi", "get friend timelin done");
		try {
			tl = api.Getter(uri);
		} catch (IllegalStateException e) {
			tl = "ランタイムエラー";
			e.printStackTrace();
		} catch (ClientProtocolException e) {
			tl = "HTTPプロトコルエラー";
			e.printStackTrace();
		} catch (IOException e) {
			tl = "入出力エラー";
			e.printStackTrace();
		}
		return tl;
	}

}

Kitwi.java

Twitroidって名前で作ってましたが、既に海外で同名のアプリが存在したので変更しました。また後で変わるかも。

import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
import android.widget.TextView;

public class Kitwi extends Activity {
    /** Called when the activity is first created. */
    static String tag = "kitwi";
	
	@Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        
        TwitterApi	api = new TwitterApi();
        
        Log.i(tag, "public TL to text");
        TextView text = new TextView(this);
		text.setText(api.getPublicTimeline());
    	setContentView(text);
	}
}