Question

I am getting Databse locking issue. I have One class which extends Activity and create instance of database there only. This is my super class

public class Example extends Activity
{

    protected DBUtil mDbUtil;
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
    mDbUtil = DBUtil.getInstance(getApplicationContext());
    }

    @Override
    public void finish() {
        super.finish();
        mDbUtil.close();
    }
}

This is my Database class

    public class DBUtil extends SQLiteOpenHelper {
    public static  DBUtil getInstance(Context context) {
            if(mInstance == null && context != null) {
                mInstance = new DBUtil(context);
                mDatabase = mInstance.getWritableDatabase();

            }
            if(mDatabase!=null && !mDatabase.isOpen())
            {
                mDatabase=mInstance.getWritableDatabase();
            }
            return mInstance;
        }


public boolean replaceOrUpdate(DBListener dbListener,final String sTable, ContentValues[] contentValues) {
        this.mDbListener=dbListener;

        if(mDatabase == null) {
            mDatabase = getWritableDatabase();
        }
        mDatabase.beginTransaction();
        try {
            int count = contentValues.length;
            for (int i=0; i<count;i++) {
                ContentValues value = contentValues[i];
                long id = mDatabase.replaceOrThrow(sTable,null,value);
                debug("Insert id = " + id);
            }
            mDatabase.setTransactionSuccessful();
            mDbListener.onCompleteInsertion();
        }catch (Exception e) {
            Log.v("Exception = " , " " + e.toString());
            e.printStackTrace();
        }finally {
            mDatabase.endTransaction();
        }
        return true;
    }

    public boolean replaceOrUpdate(final String sTable, ContentValues[] contentValues) {

        if(mDatabase == null) {
            mDatabase = getWritableDatabase();
        }
        mDatabase.beginTransaction();
        try {
            int count = contentValues.length;
            for (int i=0; i<count;i++) {
                ContentValues value = contentValues[i];
                long id = mDatabase.replaceOrThrow(sTable,null,value);
                debug("Insert id = " + id);
            }
            mDatabase.setTransactionSuccessful();
        }catch (Exception e) {
            Log.v("Exception = " , " " + e.toString());
        }finally {
            mDatabase.endTransaction();
        }
        return true;
    }

        public void close() {
            if(mDatabase != null) {
                miDbOpenCounter--;
                mDatabase.close();
            }
            mInstance = null;
            mDatabase = null;
        }

    }

My all Activity extends Example

I open Activity A(Without finishing)->Activity B(Without finishing it)->Activity C Activity c returns result and closes itself by calling finish() after insertion in Db. But while insertion it gives me mDatabase.endTransaction(); error here as nullPointer exception then Database lock exception

04-01 18:19:24.624: I/SQLiteConnectionPool(25638): The connection pool for +data+data+com_example_Example+databases+Example_db has been closed but there are still 1 connections in use.  They will be closed as they are released back to the pool.


04-01 18:19:24.624: W/System.err(25638): java.lang.NullPointerException
04-01 18:19:24.639: W/System.err(25638):    at com.example.examp.DBUtil.replaceOrUpdate(DBUtil.java:150)
04-01 18:19:24.639: W/System.err(25638):    at com.example.examp.SignupMerchant.onCompleted(SignupMerchant.java:342)
04-01 18:19:24.639: W/System.err(25638):    at com.example.examp.ExampleAsyncTask.onPostExecute(ExampleAsyncTask.java:284)
04-01 18:19:24.639: W/System.err(25638):    at com.example.examp.ExampleAsyncTask.onPostExecute(ExampleAsyncTask.java:1)
04-01 18:19:24.639: W/System.err(25638):    at android.os.AsyncTask.finish(AsyncTask.java:631)
04-01 18:19:24.639: W/System.err(25638):    at android.os.AsyncTask.access$600(AsyncTask.java:177)
04-01 18:19:24.639: W/System.err(25638):    at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:644)
04-01 18:19:24.639: W/System.err(25638):    at android.os.Handler.dispatchMessage(Handler.java:99)
04-01 18:19:24.639: W/System.err(25638):    at android.os.Looper.loop(Looper.java:176)
04-01 18:19:24.684: D/dalvikvm(25638): GC_FOR_ALLOC freed 1556K, 27% free 22981K/31248K, paused 43ms, total 43ms
04-01 18:19:24.684: W/System.err(25638):    at android.app.ActivityThread.main(ActivityThread.java:5419)
04-01 18:19:24.684: W/System.err(25638):    at java.lang.reflect.Method.invokeNative(Native Method)
04-01 18:19:24.684: W/System.err(25638):    at java.lang.reflect.Method.invoke(Method.java:525)
04-01 18:19:24.684: W/System.err(25638):    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1046)
04-01 18:19:24.684: W/System.err(25638):    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:862)
04-01 18:19:24.684: W/System.err(25638):    at dalvik.system.NativeStart.main(Native Method)


04-01 18:19:27.524: E/SQLiteLog(25638): (5) database is locked
04-01 18:19:27.544: E/SQLiteDatabase(25638): Failed to open database '/data/data/com.example.examp/databases/Example.db'.
04-01 18:19:27.544: E/SQLiteDatabase(25638): android.database.sqlite.SQLiteDatabaseLockedException: database is locked (code 5): , while compiling: PRAGMA journal_mode
04-01 18:19:27.544: E/SQLiteDatabase(25638):    at android.database.sqlite.SQLiteConnection.nativePrepareStatement(Native Method)
04-01 18:19:27.544: E/SQLiteDatabase(25638):    at android.database.sqlite.SQLiteConnection.acquirePreparedStatement(SQLiteConnection.java:1118)
04-01 18:19:27.544: E/SQLiteDatabase(25638):    at android.database.sqlite.SQLiteConnection.executeForString(SQLiteConnection.java:825)

any idea to get out of this?

Was it helpful?

Solution

Your close() method nulls the static variables shared between all activities regardless of the database being still open in some other activity.

Consider redesigning your app so that you don't have static variables here. It's perfectly ok for each activity to create a database connection of its own.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top