与服务器的连接丢失时 Android 应用程序崩溃

标签 android wcf httpurlconnection

在调试 WCF 服务时,我遇到了这个问题。我使用 HttpURLConnection 与服务进行通信。在调试服务时,我遇到一个问题,当 Android 应用程序等待响应时,我必须停止服务器,导致 Android 应用程序意外停止。

处理服务器意外突然停止并让 Android 客户端优雅地处理它的最佳方法是什么。我通过 AsyncTask 在后台工作请求/响应:

@Override
    protected JSONObject doInBackground( BLHttpJSONPostModel ...models) {
        JSONObject jsonObject = null;

        BLHttpJSONPostModel postModel = models[0];
        URL url = null;
        byte[] postData = null;
        String protocol = null;
        String response = null;
        InputStream responseStream = null;
        OutputStream outStream = null;
        HttpURLConnection connection = null;
        BufferedReader bufferedReader = null;
        StringBuilder builder = null;

        try {
            url = new URL( postModel.getUrlString() );
            postData = postModel.getPostDataAsJsonObject().toString().getBytes();
            protocol = url.getProtocol();
        } catch (MalformedURLException e1) {
            e1.printStackTrace();
            return null;
        }

        if ( protocol.equals("https") ) {
            connection = this.setUpHttps( url );    // establishes a secure connection if protocol is HTTPS
        }
        else if ( protocol.equals("http") ) {
            try {
                connection = (HttpURLConnection)url.openConnection();   // establishes un-secured connection
            } catch (IOException e) {
                e.printStackTrace();
                return null;
            }
        }
        else
            return null;    // handles unsupported protocol

        try {
            connection.setRequestProperty("Content-Length", String.valueOf(postData.length));
            connection.setRequestProperty("CONTENT-TYPE", "application/json" );
            connection.setRequestMethod( "POST" );
            connection.setUseCaches( false );
            connection.setDoInput( true );
            connection.setDoOutput( true );
            connection.connect();
            outStream = connection.getOutputStream();
            outStream.write(postData);
            outStream.close();

            String _type = connection.getContentType();         // for debugging only
            String _message = connection.getResponseMessage();  // ""
            int size = connection.getContentLength();           // ""

            bufferedReader = new BufferedReader( new InputStreamReader(connection.getInputStream(), "UTF-8") );
            builder = new StringBuilder();

            while( (response = bufferedReader.readLine()) != null ) {
                builder.append(response);
            }
        } catch (IOException e) {
            e.printStackTrace();   // no exceptio caught here
        } finally {
            connection.disconnect();
        }

        if ( (builder != null) && (! builder.toString().equals("")) ) {
            try {
                jsonObject = new JSONObject( builder.toString() );
            } catch (JSONException e) {
                e.printStackTrace();
            }
        }

        return jsonObject;
    }

堆栈跟踪:

02-20 12:13:33.935: E/AndroidRuntime(1173): FATAL EXCEPTION: AsyncTask #1
02-20 12:13:33.935: E/AndroidRuntime(1173): java.lang.RuntimeException: An error occured while executing doInBackground()
02-20 12:13:33.935: E/AndroidRuntime(1173):     at android.os.AsyncTask$3.done(AsyncTask.java:200)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at java.util.concurrent.FutureTask$Sync.innerSetException(FutureTask.java:273)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at java.util.concurrent.FutureTask.setException(FutureTask.java:124)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:307)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at java.util.concurrent.FutureTask.run(FutureTask.java:137)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1068)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:561)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at java.lang.Thread.run(Thread.java:1096)
02-20 12:13:33.935: E/AndroidRuntime(1173): Caused by: java.lang.NullPointerException
02-20 12:13:33.935: E/AndroidRuntime(1173):     at java.io.Reader.<init>(Reader.java:65)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at java.io.InputStreamReader.<init>(InputStreamReader.java:93)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at com.beslogic.remotpayment.connection.PostJSONTask.doInBackground(PostJSONTask.java:136)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at com.beslogic.remotpayment.connection.PostJSONTask.doInBackground(PostJSONTask.java:1)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at android.os.AsyncTask$2.call(AsyncTask.java:185)
02-20 12:13:33.935: E/AndroidRuntime(1173):     at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:305)
02-20 12:13:33.935: E/AndroidRuntime(1173):     ... 4 more

最佳答案

我经常遇到这个问题。问题(由于某种原因)是您捕获的 Exception 对象 e 可能为 null。在您的 try catch 语句中,执行以下操作:

try {
    // Network code
} catch(Exception e) {
    if(e != null) {
        e.printStackTrace();
    } else {
        Log.i(appLogTag, "Error: I/O Error");
    }
}

对两个 try ... catch block 都执行此操作。我知道我现在的解决方案听起来很荒谬,但我经常遇到这种情况,足以假设您可能面临同样的问题。

关于与服务器的连接丢失时 Android 应用程序崩溃,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9365151/

相关文章:

android - 如何使用处理程序线程进行多线程

android - Jenkins - 使用 Genymotion VM 而不是 Android Emulator

wcf - Web 服务响应 XML 检索 'DestinationUnreachable' 消息

javascript - WCF 服务接受简单的 JSON 字符串但拒绝带有 400 错误的 JSON 集

java - java中的HTTPS和HTTP连接

java - Android - twitter4j Proguard 错误

android - listview 不在RelativeLayout 内滚动

wcf - WCFStorm 是否支持调用启用了 JSON 的 WCF 服务?

android - 简单的 HttpURLConnection POST 文件 multipart/form-data 从 android 到 google blobstore

java - HttpURLConnection - "https://"与 "http://"