Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 5dee7aff authored by Chris Wren's avatar Chris Wren
Browse files

restore app favorites and screens

version 0: restore assuming apps are already installed.

Bug: 10779035
Change-Id: I7f9aa418a7d3d5460a79a229c0fbc80305b5eb5c
parent 1ae293c6
Loading
Loading
Loading
Loading
+77 −8
Original line number Original line Diff line number Diff line
@@ -38,6 +38,7 @@ import android.appwidget.AppWidgetManager;
import android.appwidget.AppWidgetProviderInfo;
import android.appwidget.AppWidgetProviderInfo;
import android.content.ComponentName;
import android.content.ComponentName;
import android.content.ContentResolver;
import android.content.ContentResolver;
import android.content.ContentValues;
import android.content.Context;
import android.content.Context;
import android.content.Intent;
import android.content.Intent;
import android.database.Cursor;
import android.database.Cursor;
@@ -331,9 +332,15 @@ public class LauncherBackupHelper implements BackupHelper {
        if (DEBUG) Log.d(TAG, "read (" + buffer.length + "): " +
        if (DEBUG) Log.d(TAG, "read (" + buffer.length + "): " +
                Base64.encodeToString(buffer, 0, dataSize, Base64.NO_WRAP));
                Base64.encodeToString(buffer, 0, dataSize, Base64.NO_WRAP));


        if (!mRestoreEnabled) {
            if (DEBUG) Log.v(TAG, "restore not enabled: skipping database mutation");
            return;
        }

        try {
        try {
            Favorite favorite =  unpackFavorite(buffer, 0, dataSize);
            ContentResolver cr = mContext.getContentResolver();
            if (DEBUG) Log.d(TAG, "unpacked " + favorite.itemType);
            ContentValues values = unpackFavorite(buffer, 0, dataSize);
            cr.insert(Favorites.CONTENT_URI, values);
        } catch (InvalidProtocolBufferNanoException e) {
        } catch (InvalidProtocolBufferNanoException e) {
            Log.w(TAG, "failed to decode proto", e);
            Log.w(TAG, "failed to decode proto", e);
        }
        }
@@ -363,6 +370,7 @@ public class LauncherBackupHelper implements BackupHelper {
        Set<String> currentIds = new HashSet<String>(cursor.getCount());
        Set<String> currentIds = new HashSet<String>(cursor.getCount());
        try {
        try {
            cursor.moveToPosition(-1);
            cursor.moveToPosition(-1);
            Log.d(TAG, "dumping screens after: " + in.t);
            while(cursor.moveToNext()) {
            while(cursor.moveToNext()) {
                final long id = cursor.getLong(ID_INDEX);
                final long id = cursor.getLong(ID_INDEX);
                final long updateTime = cursor.getLong(ID_MODIFIED);
                final long updateTime = cursor.getLong(ID_MODIFIED);
@@ -373,6 +381,9 @@ public class LauncherBackupHelper implements BackupHelper {
                if (!savedIds.contains(backupKey) || updateTime >= in.t) {
                if (!savedIds.contains(backupKey) || updateTime >= in.t) {
                    byte[] blob = packScreen(cursor);
                    byte[] blob = packScreen(cursor);
                    writeRowToBackup(key, blob, out, data);
                    writeRowToBackup(key, blob, out, data);
                    if (DEBUG) Log.d(TAG, "wrote screen " + id);
                } else {
                    if (DEBUG) Log.d(TAG, "screen " + id + " was too old: " + updateTime);
                }
                }
            }
            }
        } finally {
        } finally {
@@ -399,9 +410,17 @@ public class LauncherBackupHelper implements BackupHelper {
        Log.v(TAG, "unpacking screen " + key.id);
        Log.v(TAG, "unpacking screen " + key.id);
        if (DEBUG) Log.d(TAG, "read (" + buffer.length + "): " +
        if (DEBUG) Log.d(TAG, "read (" + buffer.length + "): " +
                Base64.encodeToString(buffer, 0, dataSize, Base64.NO_WRAP));
                Base64.encodeToString(buffer, 0, dataSize, Base64.NO_WRAP));

        if (!mRestoreEnabled) {
            if (DEBUG) Log.v(TAG, "restore not enabled: skipping database mutation");
            return;
        }

        try {
        try {
            Screen screen = unpackScreen(buffer, 0, dataSize);
            ContentResolver cr = mContext.getContentResolver();
            if (DEBUG) Log.d(TAG, "unpacked " + screen.rank);
            ContentValues values = unpackScreen(buffer, 0, dataSize);
            cr.insert(WorkspaceScreens.CONTENT_URI, values);

        } catch (InvalidProtocolBufferNanoException e) {
        } catch (InvalidProtocolBufferNanoException e) {
            Log.w(TAG, "failed to decode proto", e);
            Log.w(TAG, "failed to decode proto", e);
        }
        }
@@ -519,6 +538,13 @@ public class LauncherBackupHelper implements BackupHelper {
            if (icon == null) {
            if (icon == null) {
                Log.w(TAG, "failed to unpack icon for " + key.name);
                Log.w(TAG, "failed to unpack icon for " + key.name);
            }
            }

            if (!mRestoreEnabled) {
                if (DEBUG) Log.v(TAG, "restore not enabled: skipping database mutation");
                return;
            } else {
                // future site of icon cache mutation
            }
        } catch (InvalidProtocolBufferNanoException e) {
        } catch (InvalidProtocolBufferNanoException e) {
            Log.w(TAG, "failed to decode proto", e);
            Log.w(TAG, "failed to decode proto", e);
        }
        }
@@ -634,6 +660,13 @@ public class LauncherBackupHelper implements BackupHelper {
                    Log.w(TAG, "failed to unpack widget icon for " + key.name);
                    Log.w(TAG, "failed to unpack widget icon for " + key.name);
                }
                }
            }
            }

            if (!mRestoreEnabled) {
                if (DEBUG) Log.v(TAG, "restore not enabled: skipping database mutation");
                return;
            } else {
                // future site of widget table mutation
            }
        } catch (InvalidProtocolBufferNanoException e) {
        } catch (InvalidProtocolBufferNanoException e) {
            Log.w(TAG, "failed to decode proto", e);
            Log.w(TAG, "failed to decode proto", e);
        }
        }
@@ -770,11 +803,43 @@ public class LauncherBackupHelper implements BackupHelper {
    }
    }


    /** Deserialize a Favorite from persistence, after verifying checksum wrapper. */
    /** Deserialize a Favorite from persistence, after verifying checksum wrapper. */
    private Favorite unpackFavorite(byte[] buffer, int offset, int dataSize)
    private ContentValues unpackFavorite(byte[] buffer, int offset, int dataSize)
            throws InvalidProtocolBufferNanoException {
            throws InvalidProtocolBufferNanoException {
        Favorite favorite = new Favorite();
        Favorite favorite = new Favorite();
        MessageNano.mergeFrom(favorite, readCheckedBytes(buffer, offset, dataSize));
        MessageNano.mergeFrom(favorite, readCheckedBytes(buffer, offset, dataSize));
        return favorite;
        if (DEBUG) Log.d(TAG, "unpacked " + favorite.itemType + ", " + favorite.id);
        ContentValues values = new ContentValues();
        values.put(Favorites._ID, favorite.id);
        values.put(Favorites.SCREEN, favorite.screen);
        values.put(Favorites.CONTAINER, favorite.container);
        values.put(Favorites.CELLX, favorite.cellX);
        values.put(Favorites.CELLY, favorite.cellY);
        values.put(Favorites.SPANX, favorite.spanX);
        values.put(Favorites.SPANY, favorite.spanY);
        values.put(Favorites.ICON_TYPE, favorite.iconType);
        if (favorite.iconType == Favorites.ICON_TYPE_RESOURCE) {
            values.put(Favorites.ICON_PACKAGE, favorite.iconPackage);
            values.put(Favorites.ICON_RESOURCE, favorite.iconResource);
        }
        if (favorite.iconType == Favorites.ICON_TYPE_BITMAP) {
            values.put(Favorites.ICON, favorite.icon);
        }
        if (!TextUtils.isEmpty(favorite.title)) {
            values.put(Favorites.TITLE, favorite.title);
        } else {
            values.put(Favorites.TITLE, "");
        }
        if (!TextUtils.isEmpty(favorite.intent)) {
            values.put(Favorites.INTENT, favorite.intent);
        }
        values.put(Favorites.ITEM_TYPE, favorite.itemType);
        if (favorite.itemType == Favorites.ITEM_TYPE_APPWIDGET) {
            if (!TextUtils.isEmpty(favorite.appWidgetProvider)) {
                values.put(Favorites.APPWIDGET_PROVIDER, favorite.appWidgetProvider);
            }
            values.put(Favorites.APPWIDGET_ID, favorite.appWidgetId);
        }
        return values;
    }
    }


    /** Serialize a Screen for persistence, including a checksum wrapper. */
    /** Serialize a Screen for persistence, including a checksum wrapper. */
@@ -787,11 +852,15 @@ public class LauncherBackupHelper implements BackupHelper {
    }
    }


    /** Deserialize a Screen from persistence, after verifying checksum wrapper. */
    /** Deserialize a Screen from persistence, after verifying checksum wrapper. */
    private Screen unpackScreen(byte[] buffer, int offset, int dataSize)
    private ContentValues unpackScreen(byte[] buffer, int offset, int dataSize)
            throws InvalidProtocolBufferNanoException {
            throws InvalidProtocolBufferNanoException {
        Screen screen = new Screen();
        Screen screen = new Screen();
        MessageNano.mergeFrom(screen, readCheckedBytes(buffer, offset, dataSize));
        MessageNano.mergeFrom(screen, readCheckedBytes(buffer, offset, dataSize));
        return screen;
        if (DEBUG) Log.d(TAG, "unpacked " + screen.id + "/" + screen.rank);
        ContentValues values = new ContentValues();
        values.put(WorkspaceScreens._ID, screen.id);
        values.put(WorkspaceScreens.SCREEN_RANK, screen.rank);
        return values;
    }
    }


    /** Serialize an icon Resource for persistence, including a checksum wrapper. */
    /** Serialize an icon Resource for persistence, including a checksum wrapper. */
+12 −1
Original line number Original line Diff line number Diff line
@@ -138,9 +138,10 @@ public class LauncherProvider extends ContentProvider {
        if (values == null) {
        if (values == null) {
            throw new RuntimeException("Error: attempting to insert null values");
            throw new RuntimeException("Error: attempting to insert null values");
        }
        }
        if (!values.containsKey(LauncherSettings.Favorites._ID)) {
        if (!values.containsKey(LauncherSettings.BaseLauncherColumns._ID)) {
            throw new RuntimeException("Error: attempting to add item without specifying an id");
            throw new RuntimeException("Error: attempting to add item without specifying an id");
        }
        }
        helper.checkId(table, values);
        return db.insert(table, nullColumnHack, values);
        return db.insert(table, nullColumnHack, values);
    }
    }


@@ -271,6 +272,7 @@ public class LauncherProvider extends ContentProvider {
        SharedPreferences sp = getContext().getSharedPreferences(spKey, Context.MODE_PRIVATE);
        SharedPreferences sp = getContext().getSharedPreferences(spKey, Context.MODE_PRIVATE);


        if (sp.getBoolean(EMPTY_DATABASE_CREATED, false)) {
        if (sp.getBoolean(EMPTY_DATABASE_CREATED, false)) {
            Log.d(TAG, "loading default workspace");
            int workspaceResId = origWorkspaceResId;
            int workspaceResId = origWorkspaceResId;


            // Use default workspace resource if none provided
            // Use default workspace resource if none provided
@@ -882,6 +884,15 @@ public class LauncherProvider extends ContentProvider {
            mMaxItemId = id + 1;
            mMaxItemId = id + 1;
        }
        }


        public void checkId(String table, ContentValues values) {
            long id = values.getAsLong(LauncherSettings.BaseLauncherColumns._ID);
            if (table == LauncherProvider.TABLE_WORKSPACE_SCREENS) {
                mMaxScreenId = Math.max(id, mMaxScreenId);
            }  else {
                mMaxItemId = Math.max(id, mMaxItemId);
            }
        }

        private long initializeMaxItemId(SQLiteDatabase db) {
        private long initializeMaxItemId(SQLiteDatabase db) {
            Cursor c = db.rawQuery("SELECT MAX(_id) FROM favorites", null);
            Cursor c = db.rawQuery("SELECT MAX(_id) FROM favorites", null);