【发布时间】:2021-08-15 11:50:32
【问题描述】:
我是 Android 开发的新手,我正在尝试开发一个非常简单的应用程序。 我想创建一个包含一个表的预填充数据库。该表是关于用户的,它只有三列 id、name 和 professional。 该数据库的唯一用途是通过每个用户的姓名进行搜索并找到他们的职业。 所以我只需要用一些数据预填充它。
我的问题是,当我运行数据库时什么都没有发生,甚至没有创建数据库。在数据库检查器中看不到任何内容
正如我从 Room 数据库 https://developer.android.com/training/data-storage/room/prepopulate 的文档中看到的那样 我只需要添加以下代码
Room.databaseBuilder(appContext, AppDatabase.class, "Sample.db")
.createFromAsset("database/myapp.db")
.build();
所以我在 SqliteStudio 中创建了我的小型数据库,现在我尝试使用 Android 中的 Room 数据库复制它。下面你可以看到我的桌子的截图 users_table from sqliteStudio
依赖关系
// Room components
implementation "androidx.room:room-runtime:$rootProject.roomVersion"
implementation 'androidx.wear:wear:1.1.0'
annotationProcessor "androidx.room:room-compiler:$rootProject.roomVersion"
androidTestImplementation "androidx.room:room-testing:$rootProject.roomVersion"
// Lifecycle components
implementation "androidx.lifecycle:lifecycle-viewmodel:$rootProject.lifecycleVersion"
implementation "androidx.lifecycle:lifecycle-livedata:$rootProject.lifecycleVersion"
implementation "androidx.lifecycle:lifecycle-common-java8:$rootProject.lifecycleVersion"
implementation 'androidx.appcompat:appcompat:1.3.1'
implementation 'com.google.android.material:material:1.4.0'
implementation 'androidx.constraintlayout:constraintlayout:2.1.0'
testImplementation 'junit:junit:4.13.2'
androidTestImplementation 'androidx.test.ext:junit:1.1.3'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0'
compileOnly 'com.google.android.wearable:wearable:2.8.1'
implementation "androidx.lifecycle:lifecycle-extensions:2.2.0"
分级
ext {
appCompatVersion = '1.3.0'
constraintLayoutVersion = '2.0.4'
coreTestingVersion = '2.1.0'
lifecycleVersion = '2.3.1'
materialVersion = '1.3.0'
roomVersion = '2.3.0'
// testing
junitVersion = '4.13.2'
espressoVersion = '3.1.0'
androidxJunitVersion = '1.1.2'
}
您还可以看到我的 Dao、DatabaseClass、Entity、Repository、ViewModel 中的代码
用户
@Entity(tableName = "users_table")
public class User {
@PrimaryKey(autoGenerate = true)
@NonNull
private int id;
@ColumnInfo(name = "name")
@NonNull
private String name;
@ColumnInfo(name = "profession")
@NonNull
private String profession;
public User(int id, @NonNull String name, @NonNull String profession) {
this.id = id;
this.name = name;
this.profession = profession;
}
所有的 getter 和 setter 也都存在
UserDao
@Dao
public interface UserDao {
@Query("SELECT * FROM users_table")
LiveData<List<User>> getAll();
@Insert(onConflict = OnConflictStrategy.IGNORE)
void insert(User user);
@Delete
void delete(User user);
@Query("DELETE FROM users_table")
void deleteAll();
}
用户数据库
@Database(entities = {User.class}, version = 1, exportSchema = false)
public abstract class UserDatabase extends RoomDatabase {
public abstract UserDao userDao();
private static volatile UserDatabase INSTANCE;
private static final int NUM_OF_THREADS = 4;
public static final ExecutorService databaseWriteExecutor
= Executors.newFixedThreadPool(NUM_OF_THREADS);
public static UserDatabase getDatabase(final Context context){
if (INSTANCE == null){
synchronized (UserDatabase.class){
if (INSTANCE == null){
INSTANCE = Room.databaseBuilder(context.getApplicationContext(),
UserDatabase.class, "user.db")
.createFromAsset("users.db")
.build();
}
}
}
return INSTANCE;
}
}
用户存储库
public class UserRepository {
private UserDao userDao;
private LiveData<List<User>> allUsers;
public UserRepository(Application application) {
UserDatabase db = UserDatabase.getDatabase(application);
userDao = db.userDao();
allUsers = userDao.getAll();
}
public LiveData<List<User>> getAllData() { return allUsers; }
public void insert(User user){
UserDatabase.databaseWriteExecutor.execute(() -> {
userDao.insert(user);
});
}
public void deleteAll(){
UserDatabase.databaseWriteExecutor.execute(() -> {
userDao.deleteAll();
});
}
}
用户视图模型
public class UserViewModel extends AndroidViewModel {
public static UserRepository repository;
public final LiveData<List<User>> allUsers;
public UserViewModel(@NonNull Application application) {
super(application);
repository = new UserRepository(application);
allUsers = repository.getAllData();
}
public LiveData<List<User>> getAllUsers() { return allUsers; }
public static void insert(User user) { repository.insert(user); }
}
【问题讨论】:
-
是否有任何代码可以访问(或尝试)数据库?只有在进行此类尝试时,Room 才会真正打开数据库。只有在第一次打开数据库时才会进行数据库文件的复制。
-
你好@MikeT,谢谢你的回复。以上是我在项目中的确切代码。我还没有改变任何东西。当我完成代码后,我编译了项目,并且我正在将房间数据库显示给 Database Inspector ,但什么也没发生。然而类 UserDao_Impl 和 UserDatabase_Impl 已经出现...我应该添加其他东西来初始化房间数据库吗?
-
添加了一个应该澄清访问数据库的答案。 *_Impl 是根据注解生成的底层代码。这是预期的和正常的,实际上只是证明注释已被应用。注意答案是对一个常见问题的猜测。但是,它确实使用了您的代码,因此确认代码没有问题。
标签: java android android-studio android-sqlite android-room