androidandroid-sqliteandroid-database

Android db not in /data/user/0/com.programName


I am trying to locate the database created by the following code on my Android device,

public class DBAdapter extends SQLiteOpenHelper {
public DBAdapter(Context context, String name, SQLiteDatabase.CursorFactory factory) {
    super(context, name, factory, 3);
}
@Override
public void onCreate(SQLiteDatabase db) {
    db.execSQL("CREATE TABLE locationLookupDb " + "(_id INTEGER PRIMARY KEY AUTOINCREMENT, location CHAR(30))");
}

Device is running Android 15 and is rooted.

I have checked in /data/data/ as well as /data/user/0/ expecting to find a directory for the application that created the table but there is none. Running the following,

Toast.makeText(getContext(), "DB path: " + getContext().getDatabasePath("locationLookupDb.db").getAbsolutePath(), Toast.LENGTH_LONG).show();

returns "DB path: /data/user/0/com.programname/data" which is more or less what I'd expect.

Browsing to /data/user/0/ I do not see com.programname.

The table has data in it but is not showing where I anticipate it would be. Doing search queries for the table name on the device produces nothing. Is it encrypted? If that is the case how can I make it unencrypted and accessible in /data? Thanks in advance.

5/30 Update: I checked another older device running Android 10 (rooted) and found that the database files were in /data/data as anticipated. Am curious where they are now in Android 15.


Solution

  • returns "DB path: /data/user/0/com.programname/data" which is more or less what I'd expect.

    This will return the path of the potential database whether or not it exists.

    5/30 Update: I checked another older device running Android 10 (rooted) and found that the database files were in /data/data as anticipated. Am curious where they are now in Android 15.

    A common issue is the expectation that a database will exist if the class that extends SQLiteOpenHelper is instantiated. This is not the case, an attempt has to be made to access the database. The issue you describe could be due to this.

    You could force access when instantiating DBAdapter by using

    public class DBAdapter extends SQLiteOpenHelper {
    public DBAdapter(Context context, String name, SQLiteDatabase.CursorFactory factory) {
        super(context, name, factory, 3);
        this.getWritableDatabase(); /*<<<<<<<<<< ADDED to force DB access (open)*/
    }
    

    The documentation explains by saying:-

    Create a helper object to create, open, and/or manage a database. This method always returns very quickly. The database is not actually created or opened until one of getWritableDatabase() or getReadableDatabase() is called.

    Additional re Comment

    No luck. I added, " this.getWritableDatabase();" deleted the app ....

    Perhaps consider the introducing following method (or something similar) to see what the App thinks is the actual case.

    private void logDBInfo(Context context, String dbname) {
        String TAG = "DBINFO";
        String dbpath = context.getDatabasePath(dbname).getPath();
        File dbFile = new File(dbpath);
        File dbDirectory = new File(dbFile.getParent());
        boolean dbExists = dbFile.exists();
        boolean dbDirectoryExists = dbFile.getParentFile().exists();
        StringBuilder sb = new StringBuilder().append("DBInfo initiated");
        if (dbDirectoryExists) {
            sb.append("\n\t").append("DB Directory ").append(dbDirectory.getPath()).append(" FOUND");
            if (dbExists) {
                sb.append("\n\t").append("Database ").append(dbname).append("found at ").append(dbFile.getPath())
                        .append("Size is ").append(dbFile.length());
                sb.append("\n\t\t").append("Checking for related files (-wal,-shm or -journal)");
                for (String s: dbDirectory.list()) {
                    if (s.startsWith(dbname)) {
                        if (!s.equals(dbname)) {
                            sb.append("\n\t\t\t").append(s);
                        }
                    }
                }
                sb.append("\n\t\t").append("End of related files.");
            } else {
                sb.append("\n\t").append("Database ").append(dbname).append(" NOT FOUND!!!!!");
                sb.append("\n\t").append("Files (potential DB's) located in directory ").append(dbDirectory.getPath()).append(" are:-");
                for (String s:dbDirectory.list()) {
                    sb.append("\n\t\t").append(s);
                }
                sb.append("\n\tEnd of Potential Files in directory.");
            }
        } else {
            sb.append("\n\t").append("DB Directory ").append(dbDirectory.getPath()).append(" NOT FOUND!!!!!");
        }
        sb.append("\n").append("DBInfo completed");
        Log.d(TAG,sb.toString());
    }
    

    To demonstrate consider the following activity code:-

        setContentView(R.layout.activity_main);
        logDBInfo(this,MyDatabaseHelper.DATABASE_NAME);
        db = new MyDatabaseHelper(this);
        logDBInfo(this,MyDatabaseHelper.DATABASE_NAME);
        /*Cursor c = db.getWritableDatabase().query("sqlite_master",null,null,null,null,null,null);*/
        Cursor c = db.readAllLorries();
        DatabaseUtils.dumpCursor(c);
        c.close();
        logDBInfo(this,MyDatabaseHelper.DATABASE_NAME);
        logDBInfo(this,"not_a_known_database.db");
    

    So:-

    1. calls the method(no DB when App is first run)
    2. instantiates the DB Helper then calls the method (again no DB yet for first run)
    3. accesses the database then calls the method (DB now exists)
    4. calls the method BUT looking for a database named not_a_known_database.db

    The resultant LOG includes:-

    
    2025-05-31 11:09:33.198 5544-5544/a.a.so78485238javasqlitetablenotfound D/DBINFO: DBInfo initiated
            DB Directory /data/user/0/a.a.so78485238javasqlitetablenotfound/databases FOUND
            Database LazyLorry.db NOT FOUND!!!!!
            Files (potential DB's) located in directory /data/user/0/a.a.so78485238javasqlitetablenotfound/databases are:-
            End of Potential Files in directory.
        DBInfo completed
    

    As expected DB LazyLorry not found at 1. TEHN

    2025-05-31 11:09:33.199 5544-5544/a.a.so78485238javasqlitetablenotfound D/DBINFO: DBInfo initiated
            DB Directory /data/user/0/a.a.so78485238javasqlitetablenotfound/databases FOUND
            Database LazyLorry.db NOT FOUND!!!!!
            Files (potential DB's) located in directory /data/user/0/a.a.so78485238javasqlitetablenotfound/databases are:-
            End of Potential Files in directory.
        DBInfo completed
    

    AGAIN as expected DB not found THEN

    2025-05-31 11:09:33.243 5544-5544/a.a.so78485238javasqlitetablenotfound D/DBINFO: DBInfo initiated
            DB Directory /data/user/0/a.a.so78485238javasqlitetablenotfound/databases FOUND
            Database LazyLorry.dbfound at /data/user/0/a.a.so78485238javasqlitetablenotfound/databases/LazyLorry.dbSize is 49152
                Checking for related files (-wal,-shm or -journal)
                    LazyLorry.db-journal
                End of related files.
        DBInfo completed
    

    DB FOUND and seen to be in journal mode THEN for a database expected to not be found

    2025-05-31 11:09:33.243 5544-5544/a.a.so78485238javasqlitetablenotfound D/DBINFO: DBInfo initiated
            DB Directory /data/user/0/a.a.so78485238javasqlitetablenotfound/databases FOUND
            Database not_a_known_database.db NOT FOUND!!!!!
            Files (potential DB's) located in directory /data/user/0/a.a.so78485238javasqlitetablenotfound/databases are:-
                LazyLorry.db
                LazyLorry.db-journal
            End of Potential Files in directory.
        DBInfo completed
    

    DB, as expected, NOT FOUND, BUT LazyLorry.db is listed as a potential DB