Thahzan Mohomed Thahzan Mohomed - 4 months ago 129
Android Question

Eclipse says Cannot perform operation because the connection pool is closed

I'm storing some values in SQLite Database and trying to send it to MySQL on button click. Here are the relevant codes

MainActivity.java

private class SendCollections extends AsyncTask<Void, Void, Void>{

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

JSONArray json = new JSONArray();
for(int i = 0; i < dbHandler.getCollectionCount(); i++){
Bundle data = dbHandler.getCollectionDetails();

JSONObject jObject = new JSONObject();
try {
jObject.put("cust_id", data.getString("cust_id"));
jObject.put("col_id", colId);
jObject.put("method", data.getString("method"));
jObject.put("amount", data.getInt("amount"));
jObject.put("check_no", data.getInt("cheq_no"));

json.put(jObject);

} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
Log.d("Created JSON Array", json.toString());
//sendJson("http://192.168.100.172/android/json_payments.php", json);
UserFunctions userFunctions = new UserFunctions();
userFunctions.syncCollections(json.toString());

// TODO Auto-generated method stub
return null;
}



}


I'm executing the AsyncTask on button click.

UserFunctions.java

public JSONObject syncCollections(String jsonArray){

List<NameValuePair> params = new ArrayList<NameValuePair>();
params.add(new BasicNameValuePair("collections", jsonArray));
JSONObject json = jsonParser.getJSONFromUrl(sync_collections, params);

Log.d("Sending JSON Array", jsonArray);

return json;
}


JSONParser.java

public JSONObject getJSONFromUrl(String url, List<NameValuePair> params) {

// Making HTTP request
try {
// defaultHttpClient
DefaultHttpClient httpClient = new DefaultHttpClient();
HttpPost httpPost = new HttpPost(url);
httpPost.setEntity(new UrlEncodedFormEntity(params));

HttpResponse httpResponse = httpClient.execute(httpPost);
HttpEntity httpEntity = httpResponse.getEntity();
is = httpEntity.getContent();

} catch (UnsupportedEncodingException e) {
e.printStackTrace();
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}

try {
BufferedReader reader = new BufferedReader(new InputStreamReader(
is, "utf-8"), 8);
StringBuilder sb = new StringBuilder();
String line = null;
while ((line = reader.readLine()) != null) {
sb.append(line + "\n");
}
is.close();
json = sb.toString();
Log.d("JSON", json);
} catch (Exception e) {
Log.e("Buffer Error", "Error converting result " + e.toString());
}

// try parse the string to a JSON object
try {
jObj = new JSONObject(json);
} catch (JSONException e) {
Log.e("JSON Parser", "Error parsing data " + e.toString());
}

// return JSON String
return jObj;

}


DatabaseHandler.java

public Bundle getCollectionDetails(){

SQLiteDatabase db = this.getReadableDatabase();
Bundle cursorData = new Bundle();
String selectQuery = "SELECT * FROM " + TABLE_COLLECTION;
Cursor cursor = db.rawQuery(selectQuery, null);
if(cursor.moveToFirst()){
cursorData.putString("cust_id", cursor.getString(cursor.getColumnIndex(KEY_CUSTOMER_ID)));
if(cursor.getInt(cursor.getColumnIndex(KEY_CHEQ_NO)) == 0){
cursorData.putString("method", "Cash");
}else{
cursorData.putString("method", "Cheque");
}
cursorData.putInt("amount", cursor.getInt(cursor.getColumnIndex(KEY_AMOUNT)));
cursorData.putInt("cheq_no", cursor.getInt(cursor.getColumnIndex(KEY_CHEQ_NO)));
}

return cursorData;
}

public int getCollectionCount(){
String countQuery = "SELECT * FROM " + TABLE_COLLECTION;
SQLiteDatabase db = this.getReadableDatabase();
Cursor cursor = db.rawQuery(countQuery, null);
int rowCount = cursor.getCount();
db.close();
cursor.close();

return rowCount;
}


When there's only one entry in "collection" table, their seems to be no errors (as in the logcat shows the "Sending JSON Array : "). But when there's more entries, the logcat gives the following error

Logcat

02-25 10:12:05.660: E/AndroidRuntime(11394): FATAL EXCEPTION: AsyncTask #4
02-25 10:12:05.660: E/AndroidRuntime(11394): Process: collector.lbfinance, PID: 11394
02-25 10:12:05.660: E/AndroidRuntime(11394): java.lang.RuntimeException: An error occured while executing doInBackground()
02-25 10:12:05.660: E/AndroidRuntime(11394): at android.os.AsyncTask$3.done(AsyncTask.java:300)
02-25 10:12:05.660: E/AndroidRuntime(11394): at java.util.concurrent.FutureTask.finishCompletion(FutureTask.java:355)
02-25 10:12:05.660: E/AndroidRuntime(11394): at java.util.concurrent.FutureTask.setException(FutureTask.java:222)
02-25 10:12:05.660: E/AndroidRuntime(11394): at java.util.concurrent.FutureTask.run(FutureTask.java:242)
02-25 10:12:05.660: E/AndroidRuntime(11394): at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:231)
02-25 10:12:05.660: E/AndroidRuntime(11394): at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112)
02-25 10:12:05.660: E/AndroidRuntime(11394): at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587)
02-25 10:12:05.660: E/AndroidRuntime(11394): at java.lang.Thread.run(Thread.java:841)
02-25 10:12:05.660: E/AndroidRuntime(11394): Caused by: java.lang.IllegalStateException: Cannot perform this operation because the connection pool has been closed.
02-25 10:12:05.660: E/AndroidRuntime(11394): at android.database.sqlite.SQLiteConnectionPool.throwIfClosedLocked(SQLiteConnectionPool.java:962)
02-25 10:12:05.660: E/AndroidRuntime(11394): at android.database.sqlite.SQLiteConnectionPool.waitForConnection(SQLiteConnectionPool.java:599)
02-25 10:12:05.660: E/AndroidRuntime(11394): at android.database.sqlite.SQLiteConnectionPool.acquireConnection(SQLiteConnectionPool.java:348)
02-25 10:12:05.660: E/AndroidRuntime(11394): at android.database.sqlite.SQLiteSession.acquireConnection(SQLiteSession.java:894)
02-25 10:12:05.660: E/AndroidRuntime(11394): at android.database.sqlite.SQLiteSession.executeForCursorWindow(SQLiteSession.java:834)
02-25 10:12:05.660: E/AndroidRuntime(11394): at android.database.sqlite.SQLiteQuery.fillWindow(SQLiteQuery.java:62)
02-25 10:12:05.660: E/AndroidRuntime(11394): at android.database.sqlite.SQLiteCursor.fillWindow(SQLiteCursor.java:144)
02-25 10:12:05.660: E/AndroidRuntime(11394): at android.database.sqlite.SQLiteCursor.getCount(SQLiteCursor.java:133)
02-25 10:12:05.660: E/AndroidRuntime(11394): at collector.lbfinance.library.DatabaseHandler.getCollectionCount(DatabaseHandler.java:355)
02-25 10:12:05.660: E/AndroidRuntime(11394): at collector.lbfinance.AgentHome$SendCollections.doInBackground(AgentHome.java:273)
02-25 10:12:05.660: E/AndroidRuntime(11394): at collector.lbfinance.AgentHome$SendCollections.doInBackground(AgentHome.java:1)
02-25 10:12:05.660: E/AndroidRuntime(11394): at android.os.AsyncTask$2.call(AsyncTask.java:288)
02-25 10:12:05.660: E/AndroidRuntime(11394): at java.util.concurrent.FutureTask.run(FutureTask.java:237)
02-25 10:12:05.660: E/AndroidRuntime(11394): ... 4 more

Answer

Edit the method GetCollectionDetails as below.

public Bundle getCollectionDetails(){

        SQLiteDatabase db = this.getReadableDatabase();
        Bundle cursorData = new Bundle();
        String selectQuery = "SELECT * FROM " + TABLE_COLLECTION;

        Cursor cursor = db.rawQuery(selectQuery, null);
        int no_of_rows=cursor.getCount();           //count the no of rows in the database
        String[] cust_id=new String[row_count]; 
        String[] method=new String[row_count] ;
        int[] amount=new int[row_count]    
        int[] cheq_no=new int[row_count]
        int i=0;

        if(cursor.moveToFirst()){
            cust_id[i]= cursor.getString(cursor.getColumnIndex(KEY_CUSTOMER_ID));
            if(cursor.getInt(cursor.getColumnIndex(KEY_CHEQ_NO)) == 0){
                method[i]="Cash";
            }else{
                mehod[i]="Cheque";
            }
            amount[i]= cursor.getInt(cursor.getColumnIndex(KEY_AMOUNT));
            cheq_no[i]= cursor.getInt(cursor.getColumnIndex(KEY_CHEQ_NO));
             i++;
        }
        cursorData.putStringArray("cust_id",cust_id);
         cursorData.putStringArray("method",method);
        cursorData.putIntArray("amount",amount);
         cursorData.putIntArray("cheq_no",cheq_no);
        return cursorData;
    }

Then in MainActivity.java you should write the following code.

int no_of_rows=dbHandler.getCollectionCount();
String[] cust_id=new String[row_count]; String[] method=new String[row_count] ; int[] amount=new int[row_count]
int[] cheq_no=new int[row_count] int i=0; Bundle data = dbHandler.getCollectionDetails(); cust_id=data.getStringArray("cust_id"); //simililarily retrive for others

for(int i = 0; i < dbHandler.getCollectionCount(); i++){ Bundle data = dbHandler.getCollectionDetails();

    JSONObject jObject = new JSONObject();
    try {
        jObject.put("cust_id", cust_id[i]);
        json.put(jObject);
    } catch (JSONException e) {
    // TODO Auto-generated catch block
        e.printStackTrace();
    }                       
}

I hope this should work fine for you..

Comments