保留不同版本软件的持久信息

时间:2010-08-31 11:44:56

标签: android

我打算写一个免费版和一个完整版的软件。我希望完整版本也可以访问免费版软件所存储的信息(我不想使用内容提供商)。我还想确保在更新软件时不丢失这些数据。我如何实现这一目标?

1 个答案:

答案 0 :(得分:2)

您需要为sqlite帮助程序实现onUpgrade的智能方式。

您应始终拥有新的表创建查询,并使用该查询进行升级并传输任何现有数据。注意:onUpgrade方法对sqlite helper对象运行一次,你需要处理其中的所有表。

那么建议采用升级:

  • 的BeginTransaction
  • 使用if not exists运行表创建(我们正在进行升级,因此表可能尚未存在,它将无法更改和删除)
  • 列出现有列List<String> columns = DBUtils.GetColumns(db, TableName);
  • 备用表(ALTER table " + TableName + " RENAME TO 'temp_" + TableName
  • 创建新表(最新的表创建架构)
  • 获取与新列的交集,这次是从升级后的表格中取得的列(columns.retainAll(DBUtils.GetColumns(db, TableName));
  • 恢复数据(String cols = StringUtils.join(columns, ","); db.execSQL(String.format( "INSERT INTO %s (%s) SELECT %s from temp_%s", TableName, cols, cols, TableName));
  • 删除备用表(DROP table 'temp_" + TableName
  • setTransactionSuccessful

(这不会处理表降级,如果重命名列,则不会因列名不匹配而传输现有数据。)

public static List<String> GetColumns(SQLiteDatabase db, String tableName) {
    List<String> ar = null;
    Cursor c = null;
    try {
        c = db.rawQuery("select * from " + tableName + " limit 1", null);
        if (c != null) {
            ar = new ArrayList<String>(Arrays.asList(c.getColumnNames()));
        }
    } catch (Exception e) {
        Log.v(tableName, e.getMessage(), e);
        e.printStackTrace();
    } finally {
        if (c != null)
            c.close();
    }
    return ar;
}

public static String join(List<String> list, String delim) {
    StringBuilder buf = new StringBuilder();
    int num = list.size();
    for (int i = 0; i < num; i++) {
        if (i != 0)
            buf.append(delim);
        buf.append((String) list.get(i));
    }
    return buf.toString();
}