Akis Georgiou
Akis Georgiou

Reputation: 11

Android read json from restful service

I am trying to get a response from a service (the response comes in json). I made my checks if the device is connected and now I need to make the http request to the service. I found out on other questions that I have to use a background thread but I am not sure I got a working sample.

So I need to find out how I can make a connection to a given uri and read the response. My service needs to get a content header application/json in orderto return a json, so before the request I need to set this header as well.

Thank you in advance

UPDATE

package com.example.restfulapp;

import android.app.AlertDialog;
import android.app.ProgressDialog;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.net.ConnectivityManager;
import android.net.NetworkInfo;
import android.os.AsyncTask;
import android.os.Bundle;
import android.app.Activity;
import android.provider.Settings;
import org.apache.http.HttpResponse;
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 org.json.JSONObject;

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

import java.io.InputStreamReader;
import java.util.concurrent.ExecutionException;


public class MainActivity extends Activity {

    private int code = 0;
    private String value = "";
    private ProgressDialog mDialog;
    private Context mContext;
    private String mUrl ="http://192.168.1.13/myservice/upfields/";

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        if (!isOnline())
        {
            displayNetworkOption ("MyApp", "Application needs network connectivity. Connect now?");
        }

        try {
            JSONObject s = getJSON(mUrl);
        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (ExecutionException e) {
            e.printStackTrace();
        }

    }

    public class Get extends AsyncTask<Void, Void, String> {
        @Override
        protected String doInBackground(Void... arg) {
            String linha = "";
            String retorno = "";

            mDialog = ProgressDialog.show(mContext, "Please wait", "Loading...", true);

            HttpClient client = new DefaultHttpClient();
            HttpGet get = new HttpGet(mUrl);

            try {
                HttpResponse response = client.execute(get);

                StatusLine statusLine = response.getStatusLine();
                int statusCode = statusLine.getStatusCode();

                if (statusCode == 200) { // Ok
                    BufferedReader rd = new BufferedReader(new InputStreamReader(response.getEntity().getContent()));

                    while ((linha = rd.readLine()) != null) {
                        retorno += linha;
                    }
                }
            } catch (ClientProtocolException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }

            return retorno;
        }

        @Override
        protected void onPostExecute(String result) {
            mDialog.dismiss();
        }
    }

    public JSONObject getJSON(String url) throws InterruptedException, ExecutionException {
        setUrl(url);

        Get g = new Get();

        return createJSONObj(g.get());
    }

    private void displayNetworkOption(String title, String message){
        AlertDialog.Builder builder = new AlertDialog.Builder(this);
        builder
                .setTitle(title)
                .setMessage(message)
                .setPositiveButton("Wifi", new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialogInterface, int i) {
                        startActivity(new Intent(Settings.ACTION_WIFI_SETTINGS));
                    }
                })
                .setNeutralButton("Data", new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialogInterface, int i) {
                        startActivity(new Intent(Settings.ACTION_DATA_ROAMING_SETTINGS));
                    }
                })
                .setNegativeButton("No", new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialogInterface, int i) {
                        return;
                    }
                })
                .show();
    }

    private boolean isOnline() {
        ConnectivityManager cm =
                (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
        NetworkInfo netInfo = cm.getActiveNetworkInfo();
        if (netInfo != null && netInfo.isConnectedOrConnecting()) {
            return true;
        }
        return false;
    }


}

This throws errors: Gradle: cannot find symbol method setUrl(java.lang.String) Gradle: cannot find symbol method createJSONObj(java.lang.String)

Upvotes: 0

Views: 3072

Answers (3)

lory105
lory105

Reputation: 6302

From Android 3+, the http connections must be done within a separate thread. Android offers a Class named AsyncTask that help you do it.

Here you can find a good example of an AsyncTask that performs an http request and receives a JSON response.

Remember that in the doInBackgroud(..) method you CAN'T modify the UI such as to launch a Toast, to change activity or others. You have to use the onPreExecute() or onPostExecute() methods to do this.

ADD

For the mDialog and mContext variables, add the code below, and when you create the JSONTask write new JSONTask(YOUR_ACTIVITY)

public abstract class JSONTask extends AsyncTask<String, Void, String> {

  private Context context = null;
  ProgressDialog mDialog = new ProgressDialog();

  public JSONTask(Context _context){ context=_context; }

..

Upvotes: 0

Akis Georgiou
Akis Georgiou

Reputation: 11

After derogatory responses from EvZ who think that he was born knowing everything, I ended up with a subclass MyTask that I call like this inside the onCreate of my Activity.

new MyTask().execute(wserviceURL);



private class MyTask extends AsyncTask<String, Void, String> {
            @Override
            protected String doInBackground(String... urls) {
                URL myurl = null;
                try {
                    myurl = new URL(urls[0]);
                } catch (MalformedURLException e) {
                    e.printStackTrace();
                }
                URLConnection connection = null;
                try {
                    connection = myurl.openConnection();
                } catch (IOException e) {
                    e.printStackTrace();
                }

                connection.setConnectTimeout(R.string.TIMEOUT_CONNECTION);
                connection.setReadTimeout(R.string.TIMEOUT_CONNECTION);

                HttpURLConnection httpConnection = (HttpURLConnection) connection;
                httpConnection.setRequestProperty("Content-Type", getString(R.string.JSON_CONTENT_TYPE));

                int responseCode = -1;
                try {
                    responseCode = httpConnection.getResponseCode();
                } catch (SocketTimeoutException ste) {
                    ste.printStackTrace();
                }
                catch (Exception e1) {
                    e1.printStackTrace();
                }
                if (responseCode == HttpURLConnection.HTTP_OK) {
                    StringBuilder answer = new StringBuilder(100000);

                    BufferedReader in = null;
                    try {
                        in = new BufferedReader(new InputStreamReader(httpConnection.getInputStream()));
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                    String inputLine;

                    try {
                        while ((inputLine = in.readLine()) != null) {
                            answer.append(inputLine);
                            answer.append("\n");
                        }
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                    try {
                        in.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                    httpConnection.disconnect();
                    return answer.toString();
                }
                else
                {
                    //connection is not OK
                    httpConnection.disconnect();
                    return null;
                }

            }

            @Override
            protected void onPostExecute(String result) {
                String userid = null;
                String username = null;
                String nickname = null;
                if (result!=null)
                {
                    try {
                        //do read the JSON here
                    } catch (JSONException e) {
                        e.printStackTrace();
                    }
                }
                //stop loader dialog
                mDialog.dismiss();


            }

        }

lory105's answer guided me to somewhere near the answer, thanx.

Upvotes: 1

droideckar
droideckar

Reputation: 1067

here is an example of how to process the HTTP response and convert to JSONObject:

/**
 * convert the HttpResponse into a JSONArray
 * @return JSONObject
 * @param response
 * @throws IOException 
 * @throws IllegalStateException 
 * @throws UnsupportedEncodingException 
 * @throws Throwable
 */
public static JSONObject processHttpResponse(HttpResponse response) throws UnsupportedEncodingException, IllegalStateException, IOException  {
    JSONObject top = null;
    StringBuilder builder = new StringBuilder();
    try {
            BufferedReader reader = new BufferedReader(
                                        new InputStreamReader(response.getEntity().getContent(), "UTF-8"));

            for (String line = null; (line = reader.readLine()) != null;) {
                builder.append(line).append("\n");
                }

        String decoded = new String(builder.toString().getBytes(), "UTF-8");
        Log.d(TAG, "decoded http response: " + decoded);

        JSONTokener tokener = new       JSONTokener(Uri.decode(builder.toString()));

        top = new JSONObject(tokener);



  } catch (JSONException t) {
        Log.w(TAG, "<processHttpResponse> caught: " + t + ", handling as string...");

    } catch (IOException e) {
        Log.e(TAG, "caught: " + e, e);
    } catch (Throwable t) {
        Log.e(TAG, "caught: " + t, t);
    }
     return top;
}

Upvotes: 0

Related Questions