2017-04-11 27 views
0

Androidアプリでロングポーリングを使用してチャットアプリケーションを実装する際に問題が発生しています。新しいメッセージの検索はうまく動作し、HttpUrlConnectionという非同期タスクで実行されます。問題は、メッセージを送信することです。私はHttpUrlConnectionと別の非同期タスクを使用しますが、メッセージを印刷していたログによれば、新しいメッセージの検索が完了したとき、つまり長いポーリングの30秒後にのみメッセージが送信されます。 WebサービスはPHPで作られてHttpPost.javaAndroidチャットとロングポーリング

package com.roscosoft.taxifast; 

import android.os.AsyncTask; 
import android.util.Log; 

import org.json.JSONException; 
import org.json.JSONObject; 

import java.io.BufferedReader; 
import java.io.BufferedWriter; 
import java.io.InputStreamReader; 
import java.io.OutputStream; 
import java.io.OutputStreamWriter; 
import java.io.UnsupportedEncodingException; 
import java.net.HttpURLConnection; 
import java.net.MalformedURLException; 
import java.net.URL; 
import java.net.URLEncoder; 
import java.util.HashMap; 
import java.util.Map; 

import javax.net.ssl.HttpsURLConnection; 

/** 
* Created by titin on 7/12/16. 
*/ 

public class HttpPost extends AsyncTask<Void, Void, Boolean> { 
Exception error; 

public interface HttpPostInterface { 
    void termino(JSONObject obj); 
    void cancelo(String error); 
} 


public static String getPostDataString(HashMap<String, String> params) throws UnsupportedEncodingException { 
    StringBuilder result = new StringBuilder(); 
    boolean first = true; 
    for(Map.Entry<String, String> entry : params.entrySet()){ 
     if (first) 
      first = false; 
     else 
      result.append("&"); 

     result.append(URLEncoder.encode(entry.getKey(), "UTF-8")); 
     result.append("="); 
     result.append(URLEncoder.encode(entry.getValue(), "UTF-8")); 
    } 

    return result.toString(); 
} 

private StringBuilder response; 
private String postDataString; 
private String url; 
private HttpPostInterface delegate; 
private int timeout; 

HttpPost(String urlx, String postDataStringx, HttpPostInterface del) { 
    url = urlx; 
    postDataString = postDataStringx; 
    delegate = del; 
    timeout = 30000; 
} 
HttpPost(String urlx, String postDataStringx, HttpPostInterface del, int timeoutx) { 
    url = urlx; 
    postDataString = postDataStringx; 
    delegate = del; 
    timeout = timeoutx; 
} 


@Override 
protected Boolean doInBackground(Void... params) { 
    response = new StringBuilder(); 
    URL urlc = null; 
    HttpURLConnection con = null; 
    try{ 
     urlc = new URL(url); 
    }catch (MalformedURLException e){ 
     Log.i("rosco", e.getMessage()); 
     error = e; 
     return false; 
    } 
    try { 
     con = (HttpURLConnection)urlc.openConnection(); 
     con.setReadTimeout(timeout); 
     con.setConnectTimeout(timeout); 
     con.setRequestMethod("POST"); 
     con.setDoInput(true); 
     con.setDoOutput(true); 

     OutputStream os = con.getOutputStream(); 
     BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(os, "UTF-8")); 
     writer.write(postDataString); 

     writer.flush(); 
     writer.close(); 
     os.close(); 

     int responseCode = con.getResponseCode(); 
     if (responseCode == HttpsURLConnection.HTTP_OK){ 
      String line; 
      BufferedReader br = new BufferedReader(new InputStreamReader(con.getInputStream())); 
      while ((line = br.readLine()) != null){ 
       response.append(line); 
      } 
     }else{ 
      error = new Exception("Error:"+responseCode); 
      return false; 
     } 
    } catch (Exception e) { 
     Log.i("rosco", "Hubo un error al hacer el request:"+e.getMessage()); 
     error = e; 
     return false; 
    }finally { 
     con.disconnect(); 
    } 
    return true; 
} 

@Override 
protected void onPostExecute(final Boolean success) { 

    if (success) { 
     try{ 
      if (response.toString().length() == 0){ 
       if(delegate != null) delegate.cancelo("No hay respuesta del servidor"); 
      }else{ 
       //Log.i("rosco", response.toString()); // solo en desarrollo 
      } 
      JSONObject obj = new JSONObject(response.toString()); 
      if(delegate != null) delegate.termino(obj); 
     }catch (JSONException e){ 
      Log.i("rosco", "Json malformado:"+e.getMessage()+":\n"+response.toString()); 
      if(delegate != null) delegate.cancelo(response.toString()); 
     } 
    } else { 
     if(delegate != null) delegate.cancelo(error.getMessage()); 
    } 
} 

@Override 
protected void onCancelled() { 
    if(delegate != null) { 
     if (error == null) 
      delegate.cancelo("Se cancelo el request"); 
     else 
      delegate.cancelo(error.getMessage()); 
    } 
} 
} 

がフィニッシュへの最初の接続のためにサーバーが待機を受け入れるようにということも可能である:ここでは は、私が使用している非同期TASTです'メッセージを送る'接続? もしそうなら、それを修正する方法はありますか? ありがとうございます。

+0

これは、サーバーの実装に関する詳細情報なしでは回答できません。 –

答えて

0

AsyncTaskを実行するには、THREAD_POOL_EXECUTORを使用する必要があります。デフォルトの実装では、1つのスレッドで実行されるシリアル実行プログラムを使用します。

+0

ありがとう、それはトリックをしました:) –

0

すべてのAsyncTasksは、単一スレッドでシーケンスを実行します。最初のAsyncTaskは終了しませんが、2番目のタスクは開始されません。私(そして多くの開発者)はAsyncTaskの使用を推奨していません。 代替:Javaスレッド、Rx、java.util.concurrentなどのエグゼクティブ または、非同期HTTP要求を行うためにSquareなどのRetrofitライブラリを使用します。

+0

ありがとう、それは問題だった:) –

関連する問題