user1688181
user1688181

Reputation: 494

How to Handle networkonmainthreadexception in Android?

I have following 2 class

class CallNetworkMethod extends AsyncTask<Void, Void, Void>
{

    @Override
    protected Void doInBackground(Void... params) {

        if (TwitterUtils.isAuthenticated(prefs)) {
            sendTweet();
        } else {

            Intent i = new Intent(getApplicationContext(), TwPrepareRequestTokenActivity.class);
            i.putExtra("tweet_msg",getTweetMsg());
            startActivity(i);
        }

        return null;
    }

    @Override
    protected void onPostExecute(Void result) {

        // TODO Auto-generated method stub
        super.onPostExecute(result);
        //updateLoginStatus();
        loginStatus.setText("Logged into Twitter : " + TwitterUtils.isAuthenticated(prefs));
    }

}

====================================================

public class TwitterUtils {

static ArrayList<String> friens=null;

public static boolean isAuthenticated(SharedPreferences prefs) {

    String token = prefs.getString(OAuth.OAUTH_TOKEN, "");
    String secret = prefs.getString(OAuth.OAUTH_TOKEN_SECRET, "");

    AccessToken a = new AccessToken(token,secret);
    Twitter twitter = new TwitterFactory().getInstance();

    twitter.setOAuthConsumer(TwConstants.CONSUMER_KEY, TwConstants.CONSUMER_SECRET);

    twitter.setOAuthAccessToken(a);


    try {



        **twitter.getAccountSettings();**

        return true;
    } catch (TwitterException e) {
        return false;
    }
}

}

I got the exception when running this code(networkonmainthreadexception).I debug this code and found the location where exception come out. It is twitter.getAccountSettings(); .I think this method should run inside a AsynTask but i dont know how to do that.

Upvotes: 1

Views: 596

Answers (4)

Budius
Budius

Reputation: 39836

the problem is that you're using the AsyncTask wrong. The idea for the onBackground returning a value and the onPostExecute receiving a result is to pass to the UI thread something that was done on the background thread.

Something like that:

change the class CallNetworkMethod extends AsyncTask<Void, Void, Void> to

class CallNetworkMethod extends AsyncTask<Void, Void, Boolean>

change the protected Void doInBackground(Void... params) { to

protected Boolean doInBackground(Void... params) {

   Boolean result = TwitterUtils.isAuthenticated(prefs);
        if (result) {
        sendTweet();
    } else {

        Intent i = new Intent(getApplicationContext(), TwPrepareRequestTokenActivity.class);
        i.putExtra("tweet_msg",getTweetMsg());
        startActivity(i);
    }
    return result;       
}

and change the protected void onPostExecute(Void result) { to

protected void onPostExecute(Boolean result) {
    loginStatus.setText("Logged into Twitter : " + result.toString());
}

Upvotes: 1

ρяσѕρєя K
ρяσѕρєя K

Reputation: 132972

Currently you are calling TwitterUtils.isAuthenticated(prefs) in onPostExecute because onPostExecute always execute on UI thread then you are getting networkonmainthreadexception exception .

to avoid this issue use a Boolean Flag to get return from doInBackground and show it in TextView in onPostExecute as:

class CallNetworkMethod extends AsyncTask<Void, Void, Void>
{
  public static boolean status=false;
    @Override
    protected Void doInBackground(Void... params) {

       status=TwitterUtils.isAuthenticated(prefs);

        return null;
    }

    @Override
    protected void onPostExecute(Void result) {

        // TODO Auto-generated method stub
        super.onPostExecute(result);
        //updateLoginStatus();
        loginStatus.setText("Logged into Twitter : " + status);
    }

}

Upvotes: 1

Raghav Sood
Raghav Sood

Reputation: 82543

Your first call to isAuthenticated() is correctly placed in the AsyncTask. However, when you use:

loginStatus.setText("Logged into Twitter : " + TwitterUtils.isAuthenticated(prefs));

in your onPostExecute(), you're calling a networking method on the UI thread again, as onPostExecute() is run on the UI thread.

Remove this line, or store the result locally from doInBackground() and use it here.

Upvotes: 0

Archie.bpgc
Archie.bpgc

Reputation: 24012

Note that this method blocks waiting for a network response, so do not call it in a UI thread.

This is what is suggested when using:

facebook.request("me");

Same might be the case with:

twitter.getAccountSettings();

So, just like other Network connections, which you call using AsyncTasks, call this in some AsyncTask.

Okay, the Error might be here:

@Override
    protected void onPostExecute(Void result) {

        // TODO Auto-generated method stub
        super.onPostExecute(result);
        //updateLoginStatus();
        loginStatus.setText("Logged into Twitter : " + TwitterUtils.isAuthenticated(prefs));
    }

You are calling TwitterUtils.isAuthenticated(prefs) in onPostExecute();

Upvotes: 0

Related Questions