【5年Android从零复盘系列之三十二】Android存储(7):LitePal数据库框架
【代码是最好的老师】
1.概述
LitePal是郭霖大神开源的一款数据库框架。
LitePal同greendao一样,有共同的优点。
区别在,不同数据量、不同操作情形下,性能和资源占用各有些许差别。不过在2020+年代了,这些细微差别已经几乎是无感。
具体商用中,追求稳定,会更多地选择greendao。其缘由并不是LitePal性能不佳,而是greendao的有较大的使用基数,使其趋于完美。而LitePal后起之秀,及版本迭代,使用基数、开源考验度较小。
在组件化中,greendao会比litepal有优势。究其原因,是因为litepal的实体类直接继承LitepalSupport,组件化项目中 跨模块使用(数据表对应的)实体类不友好。
3.配置
step1.首先在app module的gradle依赖
//litepal step1 导包
implementation 'org.litepal.guolindev:core:3.2.3'
step2.在module下 新建文件 main/assets/litepal.xml
- 配置数据库名称
- 数据库版本号
- 表对应的实体类包名+路径
<?xml version="1.0" encoding="utf-8"?>
<litepal>
<!-- litepal step2-->
<dbname value="app" />
<version value="1" />
<!-- litepal step6 -->
<list>
<mapping class="com.cupster.func_db_litepal.entity.User"/>
<mapping class="com.cupster.func_db_litepal.entity.Article"/>
</list>
<!--
Define where the .db file should be. "internal" means the .db file
will be stored in the database folder of internal storage which no
one can access. "external" means the .db file will be stored in the
path to the directory on the primary external storage device where
the application can place persistent files it owns which everyone
can access. "internal" will act as default.
For example:
<storage value="external" />
-->
</litepal>
step3.混淆配置
-keep class org.litepal.** {
*;
}
-keep class * extends org.litepal.crud.DataSupport {
*;
}
-keep class * extends org.litepal.crud.LitePalSupport {
*;
}
step4.在app的application中初始化litepal
public class DemoApplication extends Application {
@Override
public void onCreate() {
super.onCreate();
//litepal step4
LitePalManager.init(this);
}
}
4.使用
step5.编写对应数据库表的实体类
其中,注解意义简要了解下
name | action |
---|---|
@Column | 用于向列添加约束。注意,这个注释不会影响id列 |
unique | @Column(unique = true) 约束列是唯一不可重复 |
ignore | @Column(ignore = true) 不再数据库表中创建该字段 |
nullable | @Column(nullable = false) 约束列值不为空 |
index | @Column(index = true) 给列添加索引 |
defaultValue | @Column(defaultValue = “unset”) 不考虑该列值类型,设置列的默认类型值为字符串unset |
//litepal step5
public class User extends LitePalSupport {
@Column(index = true)//这个注释不会影响id列,测试验证
private long id ;
@Column(unique = true ,defaultValue = "-")
private String name;
private int age;
private String account;
private String password;
//...
//setter & getter
step6.编写管理类,管理数据库创建、升级、删除、事务、多数据库切换等
package com.cupster.func_db_litepal;
import android.app.Application;
import org.litepal.LitePal;
import org.litepal.LitePalDB;
public class LitePalManager {
public static void init(Application application){
LitePal.initialize(application);
}
public static void newDataBase(String dbName ,int version ,Class... tables){
LitePalDB litePalDB = new LitePalDB(dbName ,version);
for (Class table: tables){
litePalDB.addClassName(table.getName());
}
LitePal.use(litePalDB);
}
public static void switchDbDefault(){
LitePal.useDefault();
}
public static void switchDB(String dbName){
LitePalDB litePalDB = LitePalDB.fromDefault(dbName);
LitePal.use(litePalDB);
}
public static void deleteDB(String dbName){
LitePal.deleteDatabase(dbName);
}
public static void beginTransaction(){
LitePal.beginTransaction();
}
public static boolean excuteTransaction(boolean... flags){
boolean success = true;
for (boolean f : flags){
if (!f){
success = false;
break;
}
}
if (success){
LitePal.setTransactionSuccessful();
}
endTransaction();
return success;
}
public static void endTransaction(){
LitePal.endTransaction();
}
}
然后就是具体场景中的使用了,这里因为才用组件化的架构,多封装了一层。
调用:
@Override
public void onClick(View view) {
switch (view.getId()){
case R.id.btn_add:
UserHelper.insert("Cupster" ,"18960222222");
break;
case R.id.btn_delete:
UserHelper.delete(1);
break;
case R.id.btn_update:
UserHelper.update(1,"Cupster改");
break;
case R.id.btn_query:
mTv.setText(UserHelper.queryAll());
break;
}
}
封装的增删改查:
package com.cupster.func_db_litepal.crud;
import com.cupster.func_db_litepal.entity.User;
import org.litepal.LitePal;
import java.util.List;
public class UserHelper {
public static boolean insert(String name ,String account){
User user1 = new User();
user1.setAccount(account);
user1.setName(name);
return user1.save();
}
public static boolean update(String name){
User user = LitePal.find(User.class , 1 );
if (user == null ){
return false;
}else {
user.setName(name);
return user.save();
}
}
public static boolean update(long id ,String name){
User user = new User();
user.setName(name);
return user.update(id)>0;
}
public static boolean delete(long id){
return LitePal.delete(User.class ,id)>0;
}
public static boolean deleteAll(){
return LitePal.deleteAll(User.class)>0;
}
public static User queryById(long id){
return LitePal.find(User.class ,id);
}
public static String queryAll(){
List<User> users = LitePal.findAll(User.class);
StringBuilder stringBuilder = new StringBuilder();
for (User u : users){
stringBuilder.append("\n");
stringBuilder.append("id:");
stringBuilder.append(u.getId());
stringBuilder.append("\n");
stringBuilder.append("name:");
stringBuilder.append(u.getName());
stringBuilder.append("\n");
stringBuilder.append("account:");
stringBuilder.append(u.getAccount());
}
return stringBuilder.toString();
}
public static List<User> queryWhere(String condition ){
return LitePal.where(condition).order("id").find(User.class);
}
}