我正在使用这个DataBaseHelper.class,我被困在onUpgrade()方法上.我不知道如何弄清楚数据库的版本号是什么.我可以将版本设置为1,第一次发布它,当我发布更新时,我只需将版本设置为2(myDataBase.setVersion(2);).但只要应用程序正在运行,它就只有2.下次启动它再次为1.私有静态int DATABASE_VERSION也是如此.我在考虑将版本号存储在一个额外的表中,但在我看来,这似乎不是最佳实践.
那么如何确保版本号在升级后增加并且保留它(分配给私有静态int DATABASE_VERSION或myDataBase.getVersion();)的值?
DataBaseHelper类:
public class DataBaseHelper extends sqliteOpenHelper {
//The Android's default system path of your application database.
private static String DB_PATH = "/data/data/com.mydatabase.db/databases/";
private static String DB_NAME = "database.sl3";
private sqliteDatabase myDataBase;
private final Context myContext;
// Do you need this?
private static int DATABASE_VERSION = 2;
// or is this correct:
// private static int DATABASE_VERSION = myDataBase.getVersion();
/**
* Constructor
* Takes and keeps a reference of the passed context in order to access to
* the application assets and resources.
*
* @param context
*/
public DataBaseHelper(Context context) {
super(context,DB_NAME,null,DATABASE_VERSION);
this.myContext = context;
}
/**
* Creates an empty database on the system and rewrites it with your own
* database.
* */
public void
createDataBase() throws IOException {
boolean dbExist = checkDataBase();
if (dbExist) {
}
else {
//By calling this method and empty database will be created into the default system path
//of your application so we are gonna be able to overwrite that database with our database.
this.getWritableDatabase();
try {
copyDataBase();
} catch (IOException e) {
throw new Error("Error copying database");
}
}
}
/**
* Check if the database already exist to avoid re-copying the file each
* time you open the application.
*
* @return true if it exists,false if it doesn't
*/
private boolean
checkDataBase() {
sqliteDatabase checkDB = null;
try {
String myPath = DB_PATH + DB_NAME;
checkDB = sqliteDatabase.openDatabase(myPath,sqliteDatabase.OPEN_READWRITE);
} catch (sqliteException e) {
//database does't exist yet.
}
if (checkDB != null) {
checkDB.close();
}
return checkDB != null ? true : false;
}
/**
* copies your database from your local assets-folder to the just created
* empty database in the
* system folder,from where it can be accessed and handled.
* This is done by transfering bytestream.
* */
private void
copyDataBase() throws IOException {
//Open your local db as the input stream
InputStream myInput = myContext.getAssets().open(DB_NAME);
// Path to the just created empty db
String outFileName = DB_PATH + DB_NAME;
//Open the empty db as the output stream
OutputStream myOutput = new FileOutputStream(outFileName);
//transfer bytes from the inputfile to the outputfile
byte[] buffer = new byte[1024];
int length;
while ((length = myInput.read(buffer)) > 0) {
myOutput.write(buffer,length);
}
//Close the streams
myOutput.flush();
myOutput.close();
myInput.close();
}
public void
openDataBase() throws sqlException {
//Open the database
String myPath = DB_PATH + DB_NAME;
myDataBase = sqliteDatabase.openDatabase(myPath,sqliteDatabase.OPEN_READWRITE);
// Which parameters do I have to pass?
onUpgrade(myDataBase,DATABASE_VERSION,2);
}
@Override
public synchronized void
close() {
if (myDataBase != null)
myDataBase.close();
super.close();
}
@Override
public void
onCreate(sqliteDatabase db) {
}
@Override
public void
onUpgrade( sqliteDatabase db,int oldVersion,int newVersion) {
Log.d ("onUpgrade first log",Integer.toString(myDataBase.getVersion()));
if (oldVersion == 1) {
// do something
// And then do this!?
DATABASE_VERSION = 2;
// or do this
myDataBase.setVersion(2);
Log.d ("onUpgrade sedond log",Integer.toString(myDataBase.getVersion()));
}
else {
Log.d("onUpgrade","else-clause: Already upgraded!");
}
}
解决方法
// Do you need this? private static int DATABASE_VERSION = 2;
是的,你需要这个. (甚至更好,也是最终的.)
这告诉数据库助手最新版本的数据库模式是什么.这应该在您的应用程序代码中修复,并在您更改架构时递增.
当您的应用程序启动时,帮助程序会在运行时检查您的代码对最新版本的想法与上次创建或升级数据库时处于活动状态的版本相同. (这就是db.getVersion()的用途.)如果数字不匹配,那么帮助程序知道存储的数据库相对于应用程序代码已经过时,因此它运行升级例程.
看起来好像您不是从头开始创建数据库,而是从资产中导入现有数据库.当您执行此初始导入时,这是确保存储的版本与您的代码版本匹配的时间;或者将其直接应用于资产中的数据库文件,或者,如果您确定资产中的数据库文件与代码匹配,则调用setVersion(DATABASE_VERSION).
在任何情况下,您都不应该尝试修改onUpgrade()例程中的版本号.只有在版本不匹配时才会调用它,并且您在此处应该做的就是进行任何更改以使数据库保持最新.升级完成后,帮助程序将管理新版本号的存储.