Android 使用Kotlin中的视图模型观察房间中的数据
我正在创建一个社交媒体应用程序,并遵循Android 使用Kotlin中的视图模型观察房间中的数据,android,viewmodel,android-room,android-livedata,android-jetpack,Android,Viewmodel,Android Room,Android Livedata,Android Jetpack,我正在创建一个社交媒体应用程序,并遵循MVVM模式 我被困在观察数据库中的数据。据我所知,Dao方法必须在后台thread上执行。但是我无法从Repository类实现viewmodel。我将粘贴代码,有人能给我一些帮助吗 Dao @Dao interface FeedDao{ //Post feed item @Insert(onConflict = OnConflictStrategy.IGNORE) fun insert(feed:Feed):Long //Update feed it
MVVM
模式
我被困在观察数据库中的数据。据我所知,Dao
方法必须在后台thread
上执行。但是我无法从Repository
类实现viewmodel
。我将粘贴代码,有人能给我一些帮助吗
Dao
@Dao
interface FeedDao{
//Post feed item
@Insert(onConflict = OnConflictStrategy.IGNORE)
fun insert(feed:Feed):Long
//Update feed item
@Update(onConflict = OnConflictStrategy.IGNORE)
fun update(feed: Feed):Int
//Get feed from user friend's
@Query("SELECT * from feed")
fun getAllFeed():LiveData<List<Feed>>
}
@Dao
接口FeedDao{
//后期提要项目
@插入(onConflict=OnConflictStrategy.IGNORE)
趣味插页(提要:提要):长
//更新提要项
@更新(onConflict=OnConflictStrategy.IGNORE)
趣味更新(提要:提要):Int
//从用户朋友的
@查询(“从提要中选择*)
fun getAllFeed():LiveData
}
存储库
class FeedRepository private constructor(private val feedDao: FeedDao) {
companion object {
@Volatile private var instance:FeedRepository? = null
private val apiClient = ApiClient.getApiClient().create(UserClient::class.java)
fun getInstance(feedDao: FeedDao)= instance?: synchronized(this){
instance ?: FeedRepository(feedDao).also { instance=it }
}
}
private fun getFeedResponse() {
//TODO:Check to change parameter values after adding Paging Functionality
val call: Call<List<Feed>> = apiClient.getFeed(20, 0)
call.enqueue(object :Callback<List<Feed>>{
override fun onFailure(call: Call<List<Feed>>?, t: Throwable?) {
Log.e("FeedRepository","Feed Callback Failure")
Timber.d(t?.message)
}
override fun onResponse(call: Call<List<Feed>>?, response: Response<List<Feed>>?) {
if(response!!.isSuccessful){
Timber.i("Successful Response -> Adding to DB")
addResponseTODB(response.body()!!)
}else{
when(response.code()){
400 -> Timber.d("Not Found 400")
500 -> Timber.d("Not logged in or Server broken")
}
}
}
})
}
private fun addResponseTODB(items:List<Feed>){
Timber.d("Response --> DB Started")
object : AsyncTask<List<Feed>,Void,Boolean>(){
override fun doInBackground(vararg params: List<Feed>?): Boolean {
var needsUpdate:Boolean = false
for(item in params[0]!!.iterator()){
var inserted = feedDao.insert(item)
if(inserted.equals(-1)){
var updated = feedDao.update(item)
if(updated > 0){
needsUpdate = true
}
}else{
needsUpdate = true
}
}
return needsUpdate
}
override fun onPostExecute(result: Boolean?) {
if (result!!){
loadFromDB()
}
}
}.execute(items)
}
private fun loadFromDB(){
Timber.d("loadFromDB")
object :AsyncTask<Void,Void,LiveData<List<Feed>>>(){
override fun doInBackground(vararg params: Void?): LiveData<List<Feed>>? {
return feedDao.getAllFeed()
}
override fun onPostExecute(result: LiveData<List<Feed>>?) {
}
}.execute()
}
public fun fetchFeed(){
Timber.d("fetchFeed")
loadFromDB()
getFeedResponse()
}
}
类FeedRepository私有构造函数(私有val feedDao:feedDao){
伴星{
@易失性私有变量实例:FeedRepository?=null
private val apiClient=apiClient.getApiClient().create(UserClient::class.java)
fun getInstance(feedDao:feedDao)=实例?:已同步(此){
实例?:FeedRepository(feedDao)。也是{instance=it}
}
}
私人娱乐getFeedResponse(){
//TODO:选中可在添加分页功能后更改参数值
val call:call=apiClient.getFeed(20,0)
排队(对象:Callback{
覆盖失效时的乐趣(调用:调用?、t:可丢弃?){
Log.e(“FeedRepository”,“Feed回调失败”)
Timber.d(t?.message)
}
覆盖fun onResponse(调用:调用?,响应:响应?){
如果(响应!!.isSuccessful){
Timber.i(“成功响应->添加到数据库”)
addResponseTODB(response.body()!!)
}否则{
当(response.code()){
400->Timber.d(“未找到400”)
500->Timber.d(“未登录或服务器损坏”)
}
}
}
})
}
私人娱乐添加响应数据库(项目:列表){
Timber.d(“响应-->数据库已启动”)
对象:AsyncTask(){
重写fun doInBackground(vararg参数:List?):布尔值{
var needsUpdate:Boolean=false
for(参数[0]中的项!!.iterator()){
插入变量=feedDao.insert(项目)
如果(插入。等于(-1)){
var updated=feedDao.update(项目)
如果(更新>0){
needsUpdate=true
}
}否则{
needsUpdate=true
}
}
返回日期
}
重写onPostExecute(结果:布尔值?){
如果(结果!!){
loadFromDB()
}
}
}.执行(项目)
}
private fun loadFromDB(){
d.木材(“荷载自DB”)
对象:AsyncTask(){
覆盖fun doInBackground(vararg参数:Void?):LiveData{
返回feedDao.getAllFeed()
}
重写onPostExecute(结果:LiveData?){
}
}.execute()
}
公共信息源(){
木材d(“FETCHTFEED”)
loadFromDB()
getFeedResponse()
}
}
视图模型
class FeedViewModel private constructor(private val
feedDao:FeedDao):ViewModel(){
// TODO: Implement the ViewModel
private val feedRepository= FeedRepository.getInstance(feedDao)
public val feed = MediatorLiveData<List<Feed>>()
val value = MutableLiveData<Int>()
init {
feed.addSource(feed,feed::setValue)
}
companion object {
private const val NO_FEED = -1
}
fun getFeedLD() = feed
}
class FeedViewModel私有构造函数(私有值
feedDao:feedDao):ViewModel(){
//TODO:实现ViewModel
private val feedRepository=feedRepository.getInstance(feedDao)
public val feed=MediatorLiveData()
val value=MutableLiveData()
初始化{
addSource(提要,提要::setValue)
}
伴星{
私有const val NO_FEED=-1
}
fun getFeedLD()=feed
}
首先,您不需要在数据库中逐个插入所有Feed
对象。您可以在FeedDao
中创建一个方法,插入List
@Insert(onConflict=OnConflictStrategy.IGNORE)
趣味插页(提要:列表):长
然后,无需在onPostExecute()
方法内调用loadFromDB()
,因为您的fun getAllFeed():LiveData()@FeedDao
中的方法返回LiveData
,您可以向其中添加Observer
,每次数据库中的数据发生更改时,都会触发Observer
对于您的网络/数据库请求,您始终可以使用NetworkBoundResource
希望我能帮上忙:)你能检查一下这个链接吗。我刚用谷歌搜索了你的问题,发现了这个。我认为这个链接可以帮助你实现ViewModel&Repository类。
@Insert(onConflict = OnConflictStrategy.IGNORE)
fun insert(feed: List<Feed>):Long