jgilfelt / chuck

An in-app HTTP inspector for Android OkHttp clients
Apache License 2.0
4.68k stars 452 forks source link

Chuck should provide a way to null out databaseHelper #63

Open changusmc opened 6 years ago

changusmc commented 6 years ago

When using Chuck in our application, I found an issue when trying to log out and logging back in.

When logging out of our application, the databaseHelper should be closed.

It doesn't seem we get that free from Chuck. I have to kill my application and relaunch it in order for the in-memory reference for databaseHelper to be cleared.

Currently, the workaround I have for our app is to use reflection to close that dbHelper when we log out of our application. Please let me know if I'm missing something or if you acknowledge this as a bug or feature request.

            ContentProvider contentProvider = getContentResolver().acquireContentProviderClient(ChuckContentProvider.TRANSACTION_URI).getLocalContentProvider();
            if (contentProvider != null && contentProvider instanceof ChuckContentProvider) {

                try {
                    ChuckContentProvider chuckContentProvider = (ChuckContentProvider) contentProvider;
                    Field databaseHelperField = chuckContentProvider.getClass().getDeclaredField("databaseHelper");
                    databaseHelperField.setAccessible(true);
                    SQLiteOpenHelper openHelper =
                            databaseHelperField.get(chuckContentProvider) instanceof SQLiteOpenHelper ? (SQLiteOpenHelper) databaseHelperField.get(chuckContentProvider)
                                                                                                      : null;
                    if (openHelper != null) {
                        openHelper.close();
                    }

                } catch (NoSuchFieldException e) {
                    logger.logp(Level.WARNING, TAG, STR_DO_CLEAN_UP, "Cannot get declared field", e);
                } catch (IllegalAccessException e) {
                    logger.logp(Level.WARNING, TAG, STR_DO_CLEAN_UP, "Cannot access private field", e);
                }
            }
sarog commented 6 years ago

I am also experiencing the same issue, surfaced via Android StrictMode.

E/StrictMode: Finalizing a Cursor that has not been deactivated or closed. database = /data/user/0/com.myapp.example/databases/chuck.db, table = 'HttpTransaction', query = SELECT _id, requestDate, tookMs, method, host, path, scheme, requestContentLength, responseCode, error, responseContentLength FROM 'HttpTransaction' ORDER BY requestDate DESC android.database.sqlite.DatabaseObjectNotClosedException: Application did not close the cursor or database object that was opened here at android.database.sqlite.SQLiteCursor.<init>(SQLiteCursor.java:98) at android.database.sqlite.SQLiteDirectCursorDriver.query(SQLiteDirectCursorDriver.java:50) at android.database.sqlite.SQLiteDatabase.rawQueryWithFactory(SQLiteDatabase.java:1722) at android.database.sqlite.SQLiteDatabase.queryWithFactory(SQLiteDatabase.java:1569) at android.database.sqlite.SQLiteDatabase.query(SQLiteDatabase.java:1440) at nl.qbusict.cupboard.DatabaseCompartment$PlatformSQLiteDatabase.query(DatabaseCompartment.java:641) at nl.qbusict.cupboard.DatabaseCompartment.query(DatabaseCompartment.java:437) at nl.qbusict.cupboard.DatabaseCompartment.access$000(DatabaseCompartment.java:53) at nl.qbusict.cupboard.DatabaseCompartment$QueryBuilder.query(DatabaseCompartment.java:586) at nl.qbusict.cupboard.DatabaseCompartment$QueryBuilder.getCursor(DatabaseCompartment.java:595) at com.readystatesoftware.chuck.internal.data.ChuckContentProvider.query(ChuckContentProvider.java:62) ...

pr-gupta commented 6 years ago

Facing the same issue. I am using the Hyperion-chuck inspector, and the app crashes with above error, when I come back to app from Chuck MainActivity