web-dev-qa-db-ja.com

java.io.IOException:androidの接続でのストリームの予期しない終了

WebサービスのURLがあり、正常に機能しています。 JSONデータを提供します。 HttpURLConnectionInputStreamを使用すると、エラーが発生します。のような

Java.io.IOException:Connection {comenius-api.sabacloud.com:443、proxy=DIRECT hostAddress = 12.130.57.1​​ cipherSuite = TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 protocol = http/1.1}(recycle count = 0)のストリームの予期しない終了

 try{
        URL url = new URL("https://comenius-api.sabacloud.com/v1/people/username="+username+":(internalWorkHistory)?type=internal&SabaCertificate="+ certificate);

        HttpURLConnection con = (HttpURLConnection)url.openConnection();
        InputStream ist = con.getInputStream();
        BufferedReader reader = new BufferedReader(new InputStreamReader(ist));

        while((singleLine = reader.readLine())!= null){
            data = data + singleLine;
            Log.e("Response", data);
        }

    }catch(Exception e)
    {
        e.printStackTrace();
    }

これを修正する方法は?

10

OKHttp3を使用しても同じ問題が発生しました。問題は、リクエストごとに接続を閉じなかったことと、クライアントに対しては同じ接続が利用でき、サーバーに対しては利用できなかったため、サーバーがエラーを返すことでした。

解決策は、接続が終了したときに接続を閉じるように各要求に示しています。これを示すには、ヘッダーにフラグを追加する必要があります。 OKHttp3は次のようになります。

Request request = new Request.Builder()
                             .url(URL)
                             .header("Connection", "close")
                             ...
17
Radost

今日、この問題に遭遇しました。そして、サーバーがエラーをスローし、リクエストを解析しているときにシャットダウンするため、サーバー障害であることがわかります。

バックエンドを確認し、自分のものでない場合は、そのサーバーの所有者に通知してください

7
grandia

私は同じ問題を抱えていましたが、エミュレーターでプロキシを構成していましたが、Charlesはもう開いていませんでした

1
Rule

解決策を見つけた
これは実際にはサーバー側の問題であり、解決策はコンテンツ長ヘッダーを送信することです
PHPを使用している場合は、次のようにコードを作成してください。

<?php
ob_start();
// the code - functions .. etc ... example:
$v = print_r($_POST,1);
$v .= "\n\r".print_r($_SERVER,1);
$file = 'file.txt';
file_put_contents($file,$v);
print $v;


// finally
$c = ob_get_contents();
$length = strlen($c);
header('Content-Length: '.$length);
header("Content-Type: text/plain");
//ob_end_flush(); // DID NOT WORK !!
ob_flush()
?>

ここで使用されるトリックは、出力バッファーを使用してコンテンツ長ヘッダーを送信することです

0
Alaa Morad

「キープアライブは、クライアントが1つの応答が終了して次の応答が開始する場所を判断することを困難にします」 1

この問題は、次の2つのケースでアライブ接続を再利用する際の衝突が原因であると思われます。

  1. サーバーは応答ヘッダーでContent-Lengthを送信しません

  2. (ストリーミングコンテンツの場合、Content-Lengthは使用できません)サーバーは使用しませんチャンク転送エンコード

そのため、例外を確認した場合は、httpヘッダーをスニッフィングします(例:Android Studio Profilerツール)。応答ヘッダーに両方が表示される場合

  • 「接続:キープアライブ」

いいえ

  • 「Content-Length:***」または「Transfer-Encoding:chunked」ヘッダー、

これが上記の場合です。

それは完全にサーバーの問題であるため、解決策は、Content-Lengthを計算し、可能であればサーバー側の応答ヘッダーに配置することです(または、チャンク転送エンコードを使用することです) )。

クライアント側で接続を閉じることを推奨することは、単なる回避策と見なす必要があります。全体的なパフォーマンスが低下することに注意してください。

0
TiMoFeJ

XAMPPを使用してlocalhostでアプリをテストしていて、このエラーが発生していました。問題は、443ポートを使用してskypeを使用していたポートにありました。

0
Tabish

これは古いスレッドである可能性があります。私にとっては、インターネット接続(Wifi)をチェックして、エンドポイントのいくつかにアクセスする際に何らかの制限があるかもしれません。

私は自分のモバイルデータを使用/接続して修正しました。

-歓声/ハッピーコーディング

0
ralphgabb