How to backup Android database - with WAL enabled - android

I know about copying the database file solutoin,
How do I backup a database file to the SD card on Android?
Android backup/restore: how to backup an internal database?
Android backup/restore: how to backup an internal database?
in fact I was backing up my databases using this method, and up until a little while ago it was working perfectly.
until some multi-thread stuff made me use of enableWriteAheadLogging
now I have two more files near the database file with .db-wal and .db-shm extensions.
copying just the datbase file .db is not working as most of the times the file does not contain the latest database commits (which are available throw app itself) however when I copy three files together it seems to work fine (not quit sure, albeit)
as Sqlite people recommend, the best practice for backing up a sqlite database is to use backup api but can someone guid me on how I can use this api from inside an application, or even use sqlite .dump (How do I dump the data of some SQLite3 tables?) method from inside an app ?
So Which one is the best practice to back up a sqlite database from an android app?
1- Copy all the database-related files from the sandbox
2- Use sqlite Backup Api
3- Use sqlite .dump
4- any other method

The SQLite backup API is the only mechanism that works correctly with concurrent write accesses from other threads/processes. Which of course means that the Android database framework does not give you access to it.
If you are sure that there are not any active connections, you can just copy all files. (Leaving out journal or WAL files would lead to data corruption.) In the case of WAL, the -shm file
does not contain any permanent data and could be omitted.

The VACUUM INTO command introduced in SQLite version 3.27.0 (2019-02-07) can serve as an alternative to the backup API.

Related

Empty SQLite file in Android 9

Last time I notice that my app has a problem with SQLite database backup. To do db backup I was copying *.db file from /data/data/com.pkg.app/databases/db_name.db to internal storage. To restore I copying from internal storage to /data/data/com.pkg.app/databases/db_name.db. But in Android P There is something wrong. Those db file exists but its weight is 4kB. When I opened those file by DB Browser I noticed that file is empty - there is no tables and data. It is strange because app is working correctly. The question is where should I look for db file that my app is using? Android 8 and less has no this problem. I am using emulator.
In Android P+ WAL (Write ahead logging) is turned on by default. This results in two additional files that suffix the original file name with -shm (shared memory file) and -wal (the write ahead logging).
These either need to be copied when backing up and restored or you need to backup only after ensuring that the database has been fully checkpointed, you can then delete the -shm and -wal files as part of the restore process.
An alternative is to disable WAL and use the less efficient journal mode.
You may wish to check out Database Import and Export not working in Android Pie.

Push db file to Databases folder in android

I wondered If it is possible to push db files into databases folder of an Android application either programatically or using any tool.
Thanks in advance!
Yes you can but not directly.
Typically a pre-built database would be included as an asset and copied to the databases folder for the package when the App is first run after installation.
If using this method then you should consider using SQLiteAssethelper, as using this simplifies the process.
In one of my App's I introduced a back-restore that backed-up the database and could restore from the downloads folder. If need be I can copy a database from elsewhere into the downloads folder and restore from that within the App. However obviously such a database has to have the correct structure/schema to not result in errors. So that is another way but would be at the user's discretion to do.
Obviously data/data//databases is protected so that imposes restrictions on "Pushing" data directly into the folder.

Backup SQLite database and restore it back when the Android application is installed

I am building an Android application that fetches data from a cloud database and stores it in SQLite locally so that user does not need to fetch it again and again.
Now I need to find an efficient way to predefine a few rows in the SQLite database and provide it along with the APK. Is this possible? if so, how do I achieve it?
Yes it is possible.
You follow these steps :-
You create the database externally, populating it, and copy the file to your App's assets folder.
You may have to create the folder.
If using Android SQLiteAssetHelper then you will need to create a databases folder in the assets folder.
There are various tools for Creating and Managing SQLite Databases. e.g. Db Browser for SQLite.
You then need to modify your App to copy the file from the assets folder (or assets/databases folder) and then open the database. Noting that you only do the copy if the database doesn't already exist.
Using the Android SQLiteAssetHelper simplifies this process.

Accessing SQLite database from Assets Folder without copying to user's data folder

In my iOS app I have a large (270MB), pre-populated, read-only sqlite database. I keep the data in the app bundle and query it with no problems. I do not copy the database to the user's documents folder, because it would be pointless in this situation to take up more space with a duplicate database. I have a separate much smaller database I copy to the user's documents folder to store the user's preferences. The app works just fine.
Now I'm trying to port my app to Android using Android Studio, but it does not seem possible to access the database from the assets folder. I have found plenty of documentation on database helper classes for Android, which I have tried, but the approach always seems to be to copy the database from the assets folder to the user's data folder. This would be a waste of space and also in my experience the app is unable to copy the database without crashing (maybe because of the size? I had no problems copying a smaller test database).
Is there a way to access the database without copying it to the user's data folder? If not can anyone think of another way of approaching this?
No, You can not directly write into the files of ASSETS folder in your application as the resources folders are read-only.
So You have to compulsory copy your database first from your assets folder to your sdcard and then only you will be able to read & write into it.
As GrIsHu said, you can only read database from asset folder. If you need to do more operation like create, update, delete you can do a tricks. Copy the database from assets folder to storage and then you can do anything you want.
Here is a quick example of Working with Android Pre Built Database.
There is a easy to use library too for accessing database from assets folder. You can check [Android SQLiteAssetHelper] here.2 Good luck!

Implementing copy of Android App DB file for backup/restore is this proper way?

I am using java methods to copy my application sqlite db from the application data directory to a folder in sd and have code to restore these file back to the application data directory. Is this a proper way of doing it? Are there potential errors or data corruption since it's a database file?
It's perfectly fine to do so. SQLite files do not have any dependencies to other files, so copying them to SD card will achieve your goal. You can check the contents of SQLite files with SQLite browser if you want to make sure.
I would suggest exporting your DB to JSON format, and save that on an external location for backup/restore. That way, you can control the data you backup (maybe you want to skip backing up some confidential data?) and you can allow advanced restore features (restore only the data and not the preferences).
In order to do that, you need to represent every table with a class (if your using ORM - this is needed anyway), and then just use one of the JSON libraries, like "Gson", to get the JSON representation of the DB. After that, you can save it to some file wherever you'd like.

Categories

Resources