/*
 * Copyright (C) 2009 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.android.server;


import android.app.backup.BackupDataInput;
import android.app.backup.BackupDataOutput;
import android.app.backup.BackupAgentHelper;
import android.app.backup.FullBackup;
import android.app.backup.WallpaperBackupHelper;
import android.content.Context;
import android.os.ParcelFileDescriptor;
import android.os.ServiceManager;
import android.util.Slog;


import java.io.File;
import java.io.IOException;

/**
 * Backup agent for various system-managed data, currently just the system wallpaper
 */
public class SystemBackupAgent extends BackupAgentHelper {
    private static final String TAG = "SystemBackupAgent";

    // These paths must match what the WallpaperManagerService uses.  The leaf *_FILENAME
    // are also used in the full-backup file format, so must not change unless steps are
    // taken to support the legacy backed-up datasets.
    private static final String WALLPAPER_IMAGE_FILENAME = "wallpaper";
    private static final String WALLPAPER_INFO_FILENAME = "wallpaper_info.xml";

    private static final String WALLPAPER_IMAGE_DIR = "/data/data/com.android.settings/files";
    private static final String WALLPAPER_IMAGE = WALLPAPER_IMAGE_DIR + "/" + WALLPAPER_IMAGE_FILENAME;

    private static final String WALLPAPER_INFO_DIR = "/data/system";
    private static final String WALLPAPER_INFO = WALLPAPER_INFO_DIR + "/" +  WALLPAPER_INFO_FILENAME;


    @Override
    public void onBackup(ParcelFileDescriptor oldState, BackupDataOutput data,
            ParcelFileDescriptor newState) throws IOException {
        if (oldState == null) {
            // Ah, it's a full backup dataset, being restored piecemeal.  Just
            // pop over to the full restore handling and we're done.
            runFullBackup(data);
            return;
        }

        // We only back up the data under the current "wallpaper" schema with metadata
        WallpaperManagerService wallpaper = (WallpaperManagerService)ServiceManager.getService(
                Context.WALLPAPER_SERVICE);
        String[] files = new String[] { WALLPAPER_IMAGE, WALLPAPER_INFO };
        if (wallpaper != null && wallpaper.mName != null && wallpaper.mName.length() > 0) {
            // When the wallpaper has a name, back up the info by itself.
            // TODO: Don't rely on the innards of the service object like this!
            // TODO: Send a delete for any stored wallpaper image in this case?
            files = new String[] { WALLPAPER_INFO };
        }
        addHelper("wallpaper", new WallpaperBackupHelper(SystemBackupAgent.this, files));
        super.onBackup(oldState, data, newState);
    }

    private void runFullBackup(BackupDataOutput output) {
        fullWallpaperBackup(output);
    }

    private void fullWallpaperBackup(BackupDataOutput output) {
        // Back up the data files directly.  We do them in this specific order --
        // info file followed by image -- because then we need take no special
        // steps during restore; the restore will happen properly when the individual
        // files are restored piecemeal.
        FullBackup.backupToTar(getPackageName(), FullBackup.ROOT_TREE_TOKEN, null,
                WALLPAPER_INFO_DIR, WALLPAPER_INFO, output);
        FullBackup.backupToTar(getPackageName(), FullBackup.ROOT_TREE_TOKEN, null,
                WALLPAPER_IMAGE_DIR, WALLPAPER_IMAGE, output);
    }

    @Override
    public void onRestore(BackupDataInput data, int appVersionCode, ParcelFileDescriptor newState)
            throws IOException {
        // On restore, we also support a previous data schema "system_files"
        addHelper("wallpaper", new WallpaperBackupHelper(SystemBackupAgent.this,
                new String[] { WALLPAPER_IMAGE, WALLPAPER_INFO }));
        addHelper("system_files", new WallpaperBackupHelper(SystemBackupAgent.this,
                new String[] { WALLPAPER_IMAGE }));

        try {
            super.onRestore(data, appVersionCode, newState);

            WallpaperManagerService wallpaper = (WallpaperManagerService)ServiceManager.getService(
                    Context.WALLPAPER_SERVICE);
            wallpaper.settingsRestored();
        } catch (IOException ex) {
            // If there was a failure, delete everything for the wallpaper, this is too aggressive,
            // but this is hopefully a rare failure.
            Slog.d(TAG, "restore failed", ex);
            (new File(WALLPAPER_IMAGE)).delete();
            (new File(WALLPAPER_INFO)).delete();
        }
    }

    @Override
    public void onRestoreFile(ParcelFileDescriptor data, long size,
            int type, String domain, String path, long mode, long mtime)
            throws IOException {
        Slog.i(TAG, "Restoring file domain=" + domain + " path=" + path);

        // Bits to indicate postprocessing we may need to perform
        boolean restoredWallpaper = false;

        File outFile = null;
        // Various domain+files we understand a priori
        if (domain.equals(FullBackup.ROOT_TREE_TOKEN)) {
            if (path.equals(WALLPAPER_INFO_FILENAME)) {
                outFile = new File(WALLPAPER_INFO);
                restoredWallpaper = true;
            } else if (path.equals(WALLPAPER_IMAGE_FILENAME)) {
                outFile = new File(WALLPAPER_IMAGE);
                restoredWallpaper = true;
            }
        }

        try {
            if (outFile == null) {
                Slog.w(TAG, "Skipping unrecognized system file: [ " + domain + " : " + path + " ]");
            }
            FullBackup.restoreToFile(data, size, type, mode, mtime, outFile, true);

            if (restoredWallpaper) {
                WallpaperManagerService wallpaper =
                        (WallpaperManagerService)ServiceManager.getService(
                        Context.WALLPAPER_SERVICE);
                wallpaper.settingsRestored();
            }
        } catch (IOException e) {
            if (restoredWallpaper) {
                // Make sure we wind up in a good state
                (new File(WALLPAPER_IMAGE)).delete();
                (new File(WALLPAPER_INFO)).delete();
            }
        }
    }
}
