Different ways to access HTTP resources from Android

In this article, I invite the reader to discover the different methods to access http resources from the Android platform.
These methods can be adapted to access web services (using REST) or simply to download files !

First Method : getting an input stream given a simple url from Android using HttpURLConnection

This method is the most basic one : it allows you, using the basic HttpUrlConnection, ( contained in java.net) to get an InputStream from an Url :

You can also use the Post method, sending data in the HTTP POST payload :

But there are better ways to achieve that, using Apache HttpClient, included in android.jar (no need to add another jar, it’s included in android core)

Second Method : getting an input stream given a simple url from Android using HttpClient

Why is it a better to do it ? because the simpler, the better ! See by yourself :

But you maybe wondering if it’s still easy with HTTP Post method ? You won’t be deceived !

But what if you want to read a cookie from the response ? And how can you send a cookie back to the server for the next request ?

Reading / Sending a cookie along with the requests

Using Apache HttpClient, it’s easy to retrieve cookies ! Everything is in the headers after all !

To send a cookie along with your request, keep it simple :

What about the resulting InputStream ? You definitely want to transform it into a String or an Drawable (to set it to an ImageView for example !) don’t you ?

Converting the InputStream into a Drawable in Android

The Drawable class already handles that for you :

Converting the InputStream into a String in Android

This is some classic java stuff (don’t tell about how easier it is in Ruby.. I know 🙁 … but hey ! Java SE7 at the rescue with NIO !!! maybe one day in 2010 ! )

62 réflexions au sujet de « Different ways to access HTTP resources from Android »

  1. Hi Anthony,
    I tryed both methods to get http resources described above, very similar to other examples I found on the web, but I can’t manage them to work.
    I always get the following exception:

    INFO/System.out(278): Excpetion = java.net.UnknownHostException: oxavi.com

    It seems it’s the same problem described by Bipin Vayalu but I can’t see any reply on this.
    I added to my AndroidManifest file the user permission:

    android:name= »android.permission.INTERNET »

    but it didn’t solve the problem.
    I tryed both on my HW(HTC WildFire android 2.2.1) and on the AVDs with no results.
    Do I miss some important configuration for the internet access ?

    Do you think it is possible to handle the http connection directly into the event handler or I need to create a separate thread ?

    =============== This is the code =====================
    final Button buttonSearch = (Button) findViewById(R.id.search);
    buttonSearch.setOnTouchListener(new View.OnTouchListener() {
    @Override
    public boolean onTouch(View v, MotionEvent event)
    {
    if(event.getAction() == android.view.MotionEvent.ACTION_DOWN){
    try {
    System.out.println(« \n\n BUTTON PUSHED\n\n »);
    InputStream content = null;
    HttpGet httpGet = new HttpGet(« http://oxavi.com/price.php »);
    HttpClient httpclient = new DefaultHttpClient();
    // Execute HTTP Get Request
    HttpResponse response = httpclient.execute(httpGet);
    content = response.getEntity().getContent();
    BufferedReader rd = new BufferedReader(new InputStreamReader(content), 4096);
    String line;
    StringBuilder sb = new StringBuilder();
    while ((line = rd.readLine()) != null)
    { sb.append(line);}
    rd.close();
    String contentOfMyInputStream = sb.toString();
    System.out.println(contentOfMyInputStream);

    } catch (Exception e){
    System.out.println(« Excpetion =  » + e);}
    }
    return true;
    }
    });
    ===================================================
    Many thanks in advance.
    Andrea

  2. Reading / Sending a cookie along with the requests.can you provide entire code for this i was struggle with this lot. please.

  3. Hi Anthony,

    You may find this somehow unrelated to your efforts towards accessing http resources from Android but I will appreciate it if you can provide me with your thoughts regarding to my challenge.

    I’m trying to capture some statistics like number of 302’s and 200 Oks or the time it takes for the client to receive the content from the streamer (time it takes from the actual request (URL) to the http client till http client sends the content back to the media player). The cleanest way to do this is to extend HttpClient code. The challenge for me is to know that if the media player (any kind) on Android will use my extended version of HttpClient or not. I will appreciate it if you can help me at least based on your experience what you think about this.

    Cheers, STZ

  4. Maybe you could use convertStreamToString to convert the InputStream into a string:


    JSONObject jsonResponse = new JSONObject(convertStreamToString(instream));


  5. ByteArrayOutputStream stream_bytes=new ByteArrayOutputStream();
    int cnt=0;
    byte[] buffer=new byte[512];
    while ((cnt=stream_content.read(buffer))!=-1)
    {stream_bytes.write(buffer, 0, cnt);
    }
    String response_text=new String(stream_bytes.toByteArray());

    or

    BufferedReader br=new BufferedReader(new InputStreamReader(stream_content), 4096);
    String line;
    StringBuilder sb=new StringBuilder();
    while ((line=br.readLine())!=null)
    {sb.append(line);
    }
    String contentOfMyInputStream=sb.toString();

  6. hi Andrea
    i have faced such problem of unknown host .
    check your internet connection ..
    or if you are testing with emulator so set dns server for emulator like

    start cmd
    change directory to android-sdk/tools
    and
    fire this command

    emulator.exe -avd [your avd name] -dns-server 192.168.1.1

    thats it.

    run your app…

    hope this will help you

  7. I think the best way how to get String content from InputStrem is:

    BufferedReader br=new BufferedReader(new InputStreamReader(inputStream, "UTF-8"));
    
    StringBuilder sb=new StringBuilder();
    
    char[] buffer = new char[8192];
    int len;
    
    while ((len = br.read(buffer)!= -1) {
      sb.append(buffer, 0, len);
    }
    
    String content = sb.toString();
    

    Note: Don’t forget on right charset, see second parameter in InputStreamReader constructor.

  8. package mainpackage.rest_client;

    import mainpackage.rest_client.R;

    import mainpackage.rest_client.util.*;
    import android.os.Bundle;
    import android.os.Handler;
    import android.app.Activity;
    import android.content.Intent;
    import android.util.Patterns;
    import android.view.Menu;
    import android.view.MenuItem;
    import android.view.View;
    import android.widget.EditText;
    import android.widget.ImageButton;
    import android.widget.Toast;

    public class MainActivity extends Activity {
    protected static final boolean TOGGLE_ON_CLICK = false;
    private SystemUiHider mSystemUiHider;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    final View contentView = findViewById(R.id.methlayout);

    contentView.setOnClickListener(new View.OnClickListener() {
    @Override
    public void onClick(View view) {

    if (TOGGLE_ON_CLICK) {

    mSystemUiHider.toggle();
    } else {
    mSystemUiHider.show();
    }
    }
    });

    ImageButton button = (ImageButton) findViewById(R.id.btn_send);
    button.setOnClickListener(new View.OnClickListener() {

    public void onClick(View v) {
    urlvalidate(v);
    }
    });

    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
    // Inflate the menu; this adds items to the action bar if it is present.
    getMenuInflater().inflate(R.menu.main, menu);
    return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item)
    {

    switch (item.getItemId())
    {
    /* case R.id.menu_file:
    // Single menu item is selected do something
    // Ex: launching new activity/screen or show alert message
    Toast.makeText(AndroidMenusActivity.this, « Bookmark is Selected », Toast.LENGTH_SHORT).show();
    return true;

    case R.id.menu_authentication:
    Toast.makeText(AndroidMenusActivity.this, « Save is Selected », Toast.LENGTH_SHORT).show();
    return true;*/

    case R.id.menu_request:
    startActivity(new Intent(this, MainActivity.class));
    return true;

    case R.id.menu_response:
    startActivity(new Intent(this, ResponseActivity.class));
    return true;

    /* case R.id.menu_header:
    Toast.makeText(AndroidMenusActivity.this, « Delete is Selected », Toast.LENGTH_SHORT).show();
    return true;

    case R.id.menu_setting:
    Toast.makeText(AndroidMenusActivity.this, « Preferences is Selected », Toast.LENGTH_SHORT).show();
    return true;*/

    default:
    return super.onOptionsItemSelected(item);
    }
    }
    @Override
    protected void onPostCreate(Bundle savedInstanceState) {
    super.onPostCreate(savedInstanceState);

    // Trigger the initial hide() shortly after the activity has been
    // created, to briefly hint to the user that UI controls
    // are available.
    // delayedHide(100);
    }

    /**
    * Touch listener to use for in-layout UI controls to delay hiding the
    * system UI. This is to prevent the jarring behavior of controls going away
    * while interacting with activity UI.
    */
    //View.OnTouchListener mDelayHideTouchListener = new View.OnTouchListener() {
    //@Override
    /* public boolean onTouch(View view, MotionEvent motionEvent) {
    if (AUTO_HIDE) {
    delayedHide(AUTO_HIDE_DELAY_MILLIS);
    }
    return false;
    }*/
    //};

    Handler mHideHandler = new Handler();
    Runnable mHideRunnable = new Runnable() {
    @Override
    public void run() {
    mSystemUiHider.hide();
    }
    };

    public void urlvalidate(View view){
    EditText textField = (EditText) findViewById(R.id.email_address);
    String enteredUrl = textField.getText().toString();
    if (Patterns.WEB_URL.matcher(enteredUrl).matches()) {
    startActivity(new Intent(this, ResponseExpandableListActivity.class));

    }
    else {
    Toast.makeText(this, « URL is invalid! », Toast.LENGTH_SHORT).show();
    textField.setText(«  »);
    }};

    }

  9. The code is for https post with a cookie. In line 8 of this code, I am not able to get the cookieHeader from the List. I tried few magic but failed to get it to work.

    Many thx

    public static InputStream getInputStreamFromUrl(String url) {
    InputStream content = null;
    try {
    HttpPost httpPost = new HttpPost(url);
    CookieSpecBase cookieSpecBase = new BrowserCompatSpec();
    List cookies = new ArrayList();
    cookies.add(cookieSpecBase);
    List cookieHeader = cookieSpecBase.formatCookies(cookies);
    // Setting the cookie
    httpPost.setHeader(« Cookie », cookieHeader.get(0).toString());
    HttpClient httpclient = new DefaultHttpClient();
    httpPost = new HttpPost(url);
    List nameValuePairs = new ArrayList(1);
    nameValuePairs.add(new BasicNameValuePair(« userName », « a »));
    nameValuePairs.add(new BasicNameValuePair(« password », « b »));
    httpPost.setEntity(new UrlEncodedFormEntity(nameValuePairs));
    // Execute HTTP Post Request
    HttpResponse response = httpclient.execute(httpPost);
    content = response.getEntity().getContent();
    return content;
    } catch (Throwable e) {

    }
    return null;
    }

Laisser un commentaire

Votre adresse de messagerie ne sera pas publiée.

Le temps imparti est dépassé. Merci de saisir de nouveau le CAPTCHA.