0

I'm trying to make an application which needs to connect to a local server to extract data ! when there is a connection , the application is working fine ! but when the connection is down the application wait about 15 seconds and then crash !! i have seen all possible solution in internet ! but no one worked for me ! Please need a hand to solve this problem here is the source code !

package com.example.chap6_5;

import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.nio.channels.UnresolvedAddressException;
import java.util.ArrayList;
import java.util.List;

import org.apache.http.HttpResponse;
import org.apache.http.NameValuePair;
import org.apache.http.client.HttpClient;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.conn.ConnectTimeoutException;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.message.BasicNameValuePair;
import org.json.JSONObject;

import android.app.Activity;
import android.content.Intent;
import android.os.AsyncTask;
import android.os.Bundle;
import android.util.Log;
import android.view.Menu;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;

public class MainActivity extends Activity {

    EditText Username, Password;
    TextView Error_Login;
    Button Button_Login;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        Username = (EditText) findViewById(R.id.username);
        Password = (EditText) findViewById(R.id.password);
        Error_Login = (TextView)findViewById(R.id.ErrorLogin);
        Button_Login = (Button)findViewById(R.id.login);

        Button_Login.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View arg0) {
                new DownloadTextTask().execute("http://192.168.1.100/PHP_MVC/mobile/MLogin.php");

            }
        });

    }

    @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;
    }

    // ---Connects using HTTP POST---
    public InputStream OpenHttpPOSTConnection(String url) {
        InputStream inputStream = null;
        try {
            HttpClient httpclient = new DefaultHttpClient();
            HttpPost httpPost = new HttpPost(url);


            // ---the key/value pairs to post to the server---
            List<NameValuePair> nameValuePairs = new ArrayList<NameValuePair>(2);
            nameValuePairs.add(new BasicNameValuePair("username", Username.getText().toString()
                    .toString()));
            nameValuePairs.add(new BasicNameValuePair("password", Password.getText().toString()));
            httpPost.setEntity(new UrlEncodedFormEntity(nameValuePairs));
            HttpResponse httpResponse = httpclient.execute(httpPost);
            inputStream = httpResponse.getEntity().getContent();
        }
         catch (ConnectTimeoutException  e)
         {
             Log.d("OpenHttpPOSTConnection TIMEOUT", e.getLocalizedMessage());
         }
        catch (Exception e) {
            Log.d("OpenHttpPOSTConnection", e.getLocalizedMessage());
        }
        return inputStream;
    }

    private String DownloadText(String URL) {
        int BUFFER_SIZE = 2000;
        InputStream in = null;
        try {
            in = OpenHttpPOSTConnection(URL);

        } 

        catch (Exception e) {
            Log.d("Networking", e.getLocalizedMessage());
            return "";
        }
        InputStreamReader isr = new InputStreamReader(in);
        int charRead;
        String str = "";
        char[] inputBuffer = new char[BUFFER_SIZE];
        try {
            while ((charRead = isr.read(inputBuffer)) > 0) {
                // ---convert the chars to a String---
                String readString = String
                        .copyValueOf(inputBuffer, 0, charRead);
                str += readString;
                inputBuffer = new char[BUFFER_SIZE];
            }
            in.close();
        } catch (IOException e) {
            Log.d("DownloadText", e.getLocalizedMessage());
            return "";
        }
        return str;
    }

    private class DownloadTextTask extends AsyncTask<String, Void, String> {
        protected String doInBackground(String... urls) {
            return DownloadText(urls[0]);
        }

        @Override
        protected void onPostExecute(String result) {
            try {

                JSONObject jsonObject = new JSONObject(result);
                String success = jsonObject.getString("Success");
                Toast.makeText(getBaseContext(), success, Toast.LENGTH_LONG).show();
                if (Integer.parseInt(success)==1)
                {
                    Log.d("DownloadTextTask", "success");
                    Intent i_Dashboard = new Intent(getApplicationContext(),Dashboard.class);
                    startActivity(i_Dashboard);
                    finish();
                }
                else
                {
                    Error_Login.setText("Error Login : Username/password are wrong !");
                }
                Log.d("DownloadTextTask", result);

            } catch (Exception e) {
                Log.d("DownloadText", e.getLocalizedMessage());
            }

        }
    }
}

[EDITED] the new OnCreate Method

protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        Username = (EditText) findViewById(R.id.username);
        Password = (EditText) findViewById(R.id.password);
        Error_Login = (TextView)findViewById(R.id.ErrorLogin);
        Button_Login = (Button)findViewById(R.id.login);

        Button_Login.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View arg0) {
                ConnectionDetector conn = new ConnectionDetector(getApplicationContext());
                 if(conn.isConnectingToInternet())
                 {
                     Toast.makeText(getApplicationContext(), "CONNECTEDs", Toast.LENGTH_LONG).show();
                new DownloadTextTask().execute("http://192.168.1.100/PHP_MVC/mobile/MLogin.php");
                 }
                 else
                     Toast.makeText(getApplicationContext(), "No connection", Toast.LENGTH_LONG).show();

            }
        });

    }

here is the logcat :

05-01 06:08:07.673: D/OpenGLRenderer(1276): TextureCache::get: create texture(0xb881bb38): name, size, mSize = 13, 7488, 1106852
05-01 06:08:10.773: D/OpenHttpPOSTConnection TIMEOUT(1276): Connect to /192.168.1.100:80 timed out
05-01 06:08:10.773: W/dalvikvm(1276): threadid=10: thread exiting with uncaught exception (group=0xa62b0288)
05-01 06:08:10.773: E/AndroidRuntime(1276): FATAL EXCEPTION: AsyncTask #1
05-01 06:08:10.773: E/AndroidRuntime(1276): java.lang.RuntimeException: An error occured while executing doInBackground()
05-01 06:08:10.773: E/AndroidRuntime(1276):     at android.os.AsyncTask$3.done(AsyncTask.java:299)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at java.util.concurrent.FutureTask$Sync.innerSetException(FutureTask.java:273)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at java.util.concurrent.FutureTask.setException(FutureTask.java:124)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:307)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at java.util.concurrent.FutureTask.run(FutureTask.java:137)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:230)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1076)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:569)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at java.lang.Thread.run(Thread.java:856)
05-01 06:08:10.773: E/AndroidRuntime(1276): Caused by: java.lang.NullPointerException
05-01 06:08:10.773: E/AndroidRuntime(1276):     at java.io.Reader.<init>(Reader.java:64)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at java.io.InputStreamReader.<init>(InputStreamReader.java:122)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at java.io.InputStreamReader.<init>(InputStreamReader.java:59)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at com.example.chap6_5.MainActivity.DownloadText(MainActivity.java:118)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at com.example.chap6_5.MainActivity.access$0(MainActivity.java:106)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at com.example.chap6_5.MainActivity$DownloadTextTask.doInBackground(MainActivity.java:140)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at com.example.chap6_5.MainActivity$DownloadTextTask.doInBackground(MainActivity.java:1)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at android.os.AsyncTask$2.call(AsyncTask.java:287)
05-01 06:08:10.773: E/AndroidRuntime(1276):     at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:305)
05-01 06:08:10.773: E/AndroidRuntime(1276):     ... 5 more
05-01 06:08:10.893: D/OpenGLRenderer(1276): TextureCache::get: create texture(0xb87ab998): name, size, mSize = 24, 7488, 1114340
05-01 06:08:11.329: D/OpenGLRenderer(1276): TextureCache::flush: target size: 668604
05-01 06:08:11.329: D/OpenGLRenderer(1276): TextureCache::callback: name, removed size, mSize = 2, 5184, 1109156
05-01 06:08:11.329: D/OpenGLRenderer(1276): TextureCache::callback: name, removed size, mSize = 4, 20736, 1088420
05-01 06:08:11.329: D/OpenGLRenderer(1276): TextureCache::callback: name, removed size, mSize = 10, 2304, 1086116
05-01 06:08:11.329: D/OpenGLRenderer(1276): TextureCache::callback: name, removed size, mSize = 13, 7488, 1078628
05-01 06:08:11.329: D/OpenGLRenderer(1276): TextureCache::callback: name, removed size, mSize = 6, 7488, 1071140
05-01 06:08:11.329: D/OpenGLRenderer(1276): TextureCache::callback: name, removed size, mSize = 1, 1048576, 22564

Thanks so much!

satyres
  • 377
  • 1
  • 5
  • 17

3 Answers3

2

First Method

in your OpenHttpPOSTConnection function, check for the status of the Internet

...
HttpResponse httpResponse = httpclient.execute(httpPost);
if(httpResponse.getStatusLine().getStatusCode() == 200) //which means there is connection
     inputStream = httpResponse.getEntity().getContent();
else
     return null;

then check if null get out of the AsyncTask.. by maybe providing the onPostExcute and null value, and depend of null show a toast to tell the user there is no Internet connection.

Second Method

also you can have a ConnectionDetector class where you check if there is an Internet connection prior to execute of AsyncTask..

public class ConnectionDetector {

private Context _context;

public ConnectionDetector(Context context){
    this._context = context;
}

public boolean isConnectingToInternet(){
    ConnectivityManager connectivity = (ConnectivityManager) _context.getSystemService(Context.CONNECTIVITY_SERVICE);
      if (connectivity != null) 
      {
          NetworkInfo[] info = connectivity.getAllNetworkInfo();
          if (info != null) 
              for (int i = 0; i < info.length; i++) 
                  if (info[i].getState() == NetworkInfo.State.CONNECTED)
                  {
                      return true;
                  }

      }
      return false;
   }
}

then before you execute your AysncTask:

 ConnectionDetector conn = new ConnectionDetector(getApplicationContext());
 if(conn.isConnectiontoInternet())
    new DownloadTextTask().execute("http://192.168.1.100/PHP_MVC/mobile/MLogin.php");
 else
    //show toast.

P.S: make sure you add this permission to your manifest:

<!-- Network State Permissions -->
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
Coderji
  • 7,655
  • 5
  • 37
  • 51
  • Thanks for the comment ! but the first methond didn't work for me ,i'm trying the second one ! – satyres May 01 '14 at 06:23
  • I'm sorry but still getting the same problem , the application crash even with the second method :( – satyres May 01 '14 at 06:35
  • the isConnectiontoInternet always return true ! even if shutdown my internet connection !and my local netwrok ! ;( – satyres May 01 '14 at 06:52
  • the second method shouldn't let you execute the AsyncTask... I have tested it now.. It works fine, Are you using mobile device or emulator? – Coderji May 01 '14 at 07:06
  • I tried under GenyMotion and Android Emulator and both execute isConnectiontoInternet even if i shutdown localnetwork !! i'm confused ! – satyres May 01 '14 at 07:10
  • i edited my code and added the onCreate Method normally it's right ? – satyres May 01 '14 at 07:15
  • The onCreate is Right, I know that emulators take Internet connection from your PC, if your PC is connected to the Internet so does your emulator, but turning of the Internet should make it work.. – Coderji May 01 '14 at 07:17
  • 1
    after spending 2 hours i figure out the problem is in this method :private String DownloadText(String URL) i have to throw an exception when OpenHttpPOSTConnection return null ! so thanks so much for your help all is in order ! – satyres May 02 '14 at 17:53
1

You're getting a null pointer exception. Check for nulls and then if you get a null value perform logic accordingly. Most importantly, you should check to see if you have a network connection prior to executing your network IO to help prevent these types of issues from occurring.

You can do this by following the solution listed in this question: Detect whether there is an Internet connection available on Android

Community
  • 1
  • 1
Donn Felker
  • 9,553
  • 7
  • 48
  • 66
  • I tried the function in your link ! but didn't work either ! the applcation still crash !! i don't understand why ! – satyres May 01 '14 at 06:46
  • Because you're getting a null pointer exception. Somewhere in your code you're accessing something that is null. Debug through each line and check to see if the object is null. If so, thats your problem. Once you find it, you need to figure out WHY it is null. Fix that, and then the problem is solved. – Donn Felker May 01 '14 at 06:54
  • Thanks for the comment but when the connection is working ! there is no Null point ! so the problem is with the connection ! – satyres May 01 '14 at 06:58
  • You need to take this line ` new DownloadTextTask().execute("http://192.168.1.100/PHP_MVC/mobile/MLogin.php");` and perform the connection check before that line is executed. If there is a connection, continue, otherwise do not execute that line of code. – Donn Felker May 01 '14 at 07:05
  • I did what you said ! if you want i will posted but didn't work either !! – satyres May 01 '14 at 07:11
  • i edited my code and added the onCreate Method ! so it's still wrong what i have done ! any way :) Thanks fot the help – satyres May 01 '14 at 07:14
  • i figure out the problem is in this method :private String DownloadText(String URL) i have to throw an exception when OpenHttpPOSTConnection return null ! so thanks so much for your help all is in order ! – satyres May 02 '14 at 17:54
0

This will happen if the InputStream in = null. If the network is down OpenHttpPOSTConnection will try to read from the network and will fail and throw and exception. You catch this. This will result in the function returning null, and inputstream will be null.

A null check of the return value of OpenHttpPOSTConnection will solve this

user868459
  • 288
  • 1
  • 3
  • 8
  • the problem is how can i catch this exception to prenvent the application from crashing ! – satyres May 01 '14 at 07:48
  • you can catch it in the outermost block instead of catching it inside. let OpenHttpPOSTConnection throw an IOException – user868459 May 02 '14 at 01:56