Android使用GreenDAO数据库的基本操作及数据库升级迁移

        最近遇到过一些关于Android使用GreenDAO数据库出现的问题,例如数据库的升级,出Release版本后运行出现奔溃的问题等等。在这里,小编整理下自己调试过程的一些积累与大家码友分享。

       一:关于GreenDAO数据库的配置

      关于Android工程使用GreenDAO数据库的过程,这里就不再多说,各位码友可以google去就知道了。这里小编贴出几点重要的配置先。

1.在Project的gradle配置文件中引入插件:

buildscript {
    // Define versions in single place
    ......
    dependencies {
        .....
        classpath 'org.greenrobot:greendao-gradle-plugin:3.2.2'
        .....
    }
    ......
}

2.在Module的gradle配置文件中引入如下:

     apply plugin: 'org.greenrobot.greendao'

3.在Module的dependencies依赖下添加依赖:

  dependencies {
     .....
     implementation 'org.greenrobot:greendao:3.2.2'
     implementation 'net.zetetic:android-database-sqlcipher:3.5.6'
     .....
  }

4,在Module的gradle配置中增加数据库的版本配置相关信息:

    greendao {
       schemaVersion 1
       daoPackage 'com.android.gd'
       targetGenDir 'src/main/java'
    }

ok,这时候配置完成后即可增加数据库的Bean文件抽象即可,对JAVA对象使用注解即可,如下:

@Entity() 

这时候Build AS工程GreenDAO插件将会根据注解帮我们编译生成一些数据库的实际操作代码。 

      二:关于GreenDAP数据库的升级

      关于数据库的升级小编说两点,一是在数据库中增加新的表,也就是说增加个新的java对象bean,二是在旧数据库中表中增加一个字段,这两点在实际项目开发中还是比较常用的。 

1.首先我们要实现DaoMaster.OpenHelper的子类去实现其父类的 onUpgrade函数,当数据库版本发生变化,会触发此函数的调用,代码如下:

public class MyOpenHelper extends DaoMaster.OpenHelper {
    .....
    @Override
    public void onUpgrade(Database db, int oldVersion, int newVersion) {
        Logger.debug(">>onUpgrade");
        if(oldVersion < newVersion){
            MigrationHelper.migrate(db , daoClasses);
        }
    }
    .....
}

2.下面我们需要实现数据库拷贝迁移实现类,参考网上的一些事例代码,网上大牛写的很多,主要代码如下:

/**
 * dao class already define the sql exec method, so just invoke it
 */
private static void reflectMethod(Database db, String methodName, boolean isExists, @NonNull Class>... daoClasses) {
    if (daoClasses.length < 1) {
        return;
    }
    try {
        for (Class cls : daoClasses) {
            Method method = cls.getDeclaredMethod(methodName, Database.class, boolean.class);
            method.invoke(null, db, isExists);
        }
    } catch (NoSuchMethodException e) {
        e.printStackTrace();
    } catch (InvocationTargetException e) {
        e.printStackTrace();
    } catch (IllegalAccessException e) {
        e.printStackTrace();
    }
}

3.下面需要实现自己的数据库管理函数,用于初始化一些数据库表的操作,封装常规的增删改查的基本的数据库方法,主要代码如下: 

//初始化数据库函数,供程序初始化的时候调用进行数据库表的初始化工作
public static final String mDBName = "example.db";
private DaoSession mDaoSession = null;
private ExampleBeanDao dao = null;
public void initDao(Context context, Class>... daoClasses) { 
   .....
   final ReleaseOpenHelper helper = new ReleaseOpenHelper(context, mDBName,daoClasses); 
   final Database db = helper.getWritableDb(); 
   mDaoSession = new DaoMaster(db).newSession(); 
   dao = mDaoSession.getExampleBeanDao(); 
   .....
}
//下面是数据库增删改查函数,其实GreenDAO框架为我们封装了很多功能函数,可以详细看看api函数,小编只列出来基本的函数
//增
public void add(){
   .....
   dao.insert();
   .....
}
//删
public void delete(){
   .....
   dao.delete();
   .....
}
//改
public void update(){
   .....
   dao.update();
   .....
}​​​​​​​
//查
public void find(){
   .....
   dao.queryBuilder().build().list();
   .....
}

      三:混淆配置

#GreenDAO混淆配置
-keep class org.greenrobot.greendao.**{*;}
-keep public interface org.greenrobot.greendao.**
-keepclassmembers class * extends org.greenrobot.greendao.AbstractDao {
    public static java.lang.String TABLENAME;
}
-keep class **$Properties
-keep class net.sqlcipher.database.**{*;}
-keep public interface net.sqlcipher.database.**
-dontwarn net.sqlcipher.database.**
-dontwarn org.greenrobot.greendao.**

    四:使用与调试

基本代码已经完成,当我们需要增加数据库新表时,只需修改修改初始化函数调用地方:

 例如:

1.数据库版本为1时,只有如下数据库表ExampleBeanDao

DatabaseManager.getInstance().init(this, ExampleBeanDao.class);

2.那么当程序更新新版本时,程序增加了数据库表ExampleBeanDao2,叠加上面的配置schemaVersion的值,初始化里增加:

DatabaseManager.getInstance().init(this, ExampleBeanDao.class,ExampleBeanDao2.class);

3.那么如果在ExampleBeanDao类中增加一个数据库表,直接叠加上面的配置schemaVersion的值即可

ok,数据库的两种升级场景也介绍了,那么接下来小编编译了demo程序测试验证了这两点,发现运行时出现奔溃,查看程序日志发现报告:找不到XXX数据库表。

后面分析发现,并检查了代码也未发现问题,惊奇的发现debug的apk没问题,release的不行,因此怀疑可能是混淆文件的问题,后面尝试将bean文件也保持不混淆:

-keep class com.android.gd.bean.**{*;}

再次重新编译测试,解决了此问题。

好啦,以上就是小编的简单分享,菜鸟小编还在Android的路上不断摸索,希望说的不对的地方各位大牛码友能够不吝指正,谢谢。

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

家是讲爱的地方,不是讲理的地方

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

 

 

 

 

 

 

 

 

      

你可能感兴趣的:(Android)