Skip to content
This repository has been archived by the owner on Jul 7, 2022. It is now read-only.

missing method for backing up database #18

Open
dmatora opened this issue May 14, 2016 · 7 comments
Open

missing method for backing up database #18

dmatora opened this issue May 14, 2016 · 7 comments

Comments

@dmatora
Copy link

dmatora commented May 14, 2016

Each time i deploy app, my database changes are getting lost.
Sqlite.copyDatabase is handy for restoring database from a backup, but it would be extremely helpful to have a way to backup it

@thiagoufg
Copy link

I'm also interested in that feature

@NathanaelA
Copy link
Owner

Not fully following the feature request now that I am looking into it. What exact issue are you trying to solve?

@sarfraznawaz2005
Copy link

@NathanaelA I also need the same feature. Sqlite.copyDatabase is handy but reverse should also be possible. We want in our apps for example ability for users to backup database/data and restore it after they uninstall app and install again.

@leungkimming
Copy link

I urgently require this feature. Every time I install a new version of my App, all existing data in SQLITE will be gone! Please provide a way to retain SQLITE data when install new App version!!!

@sarfraznawaz2005
Copy link

This is how I am doing it manually, it actually copies database to external storage and then I can restore it from within the app whenever needed. Not using copyDatabase() or any function of this package.

XML:

        <Label text="Backup Data" class="heading text-muted m-t-20" />

        <GridLayout columns="*, *" rows="auto">
            <Button col="0" text="&#xf093; Backup Data" class="btnSuccess" tap="{{ onBackupData }}" />
            <Button col="1" text="&#xf019; Restore Data" class="btnPrimary" tap="{{ onRestoreData }}" />
        </GridLayout>

Backup Restore JS Code:

const observable = require("data/observable");
const appSettings = require("application-settings");
const fileSystemModule = require("file-system");
const Toast = require("nativescript-toast");
const dialogs = require("ui/dialogs");
const permissions = require("nativescript-permissions");

const settings = new observable.Observable();

const packageName = "com.example.myApp";
const dbName = "backupName.db";

settings.onBackupData = function () {

    // ask for needed permissions
    permissions.requestPermission(android.Manifest.permission.WRITE_EXTERNAL_STORAGE, "Please allow storage read permission for backup creation.")
        .then()
        .catch();

    permissions.requestPermission(android.Manifest.permission.READ_EXTERNAL_STORAGE, "Please allow storage write permission for backup reading.")
        .then()
        .catch();

    const rootPath = android.os.Environment.getExternalStorageDirectory().getAbsolutePath().toString();
    const path = fileSystemModule.path.join(rootPath, dbName);

    dialogs.confirm("Continue with data backup ?").then((result) => {
        if (result) {
            const source = `/data/data/${packageName}/databases/${dbName}`;

            copyAndroidFileUsingStream(source, path);
        }
    });
};

settings.onRestoreData = function () {

    // ask for needed permissions
    permissions.requestPermission(android.Manifest.permission.WRITE_EXTERNAL_STORAGE, "Please allow storage read permission for backup creation.")
        .then()
        .catch();

    permissions.requestPermission(android.Manifest.permission.READ_EXTERNAL_STORAGE, "Please allow storage write permission for backup reading.")
        .then()
        .catch();

    dialogs.confirm("Existing data will be lost, continue ?").then((result) => {
        if (result) {

            const rootPath = android.os.Environment.getExternalStorageDirectory().getAbsolutePath().toString();
            const source = fileSystemModule.path.join(rootPath, dbName);
            const path = `/data/data/${packageName}/databases/${dbName}`;
            console.log(source);

            copyAndroidFileUsingStream(source, path);
        }
    });
};

// works in android only
function copyAndroidFileUsingStream(source, dest) {
    let is = null;
    let os = null;

    try {
        is = new java.io.FileInputStream(source);
        os = new java.io.FileOutputStream(dest);
        // let buffer = Array.create("byte", 1024);
        const buffer = Array.create("byte", 4096);
        let length = 0;
        // tslint:disable-next-line:no-conditional-assignment
        while ((length = is.read(buffer)) > 0) {
            os.write(buffer, 0, length);
        }
    }
    catch (e) {
        this.errorService.handleError(e);
    }
    finally {
        console.log("copy done");
        Toast.makeText("Operation Completed!").show();
        is.close();
        os.close();
    }
}

exports.SettingsViewModel = settings;

The code uses two external packages that is nativescript-toast and nativescript-permissions, if you don't need it, modify the above code accordingly.

Also make sure to request for required permissions in manifest file:

	<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
	<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>

Hope that helps.

@leungkimming
Copy link

@sarfraznawaz2005 Thanks for your reply. Unfortunately I need to use JavaScript on IOS. Any other suggestion? Or, do you know a way that Nativescript sidekick "run on device" won't clean up my sqlite DB when building and running a new version.

@sarfraznawaz2005
Copy link

sarfraznawaz2005 commented Dec 16, 2018

@leungkimming I haven't worked with IOS so I have no idea about it but I am sure there must be some way or command line way of pulling and pushing db in development mode similar to adb pull and adb push in android. So your best bet would be to ask this in IOS forum or support center.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests

5 participants