Add Nextcloud News classic synchronization

This commit is contained in:
Shinokuni 2024-06-16 16:06:48 +02:00
parent 5bff505fc3
commit e723dee12e
3 changed files with 81 additions and 32 deletions

View File

@ -12,6 +12,7 @@ import com.readrops.db.entities.Feed
import com.readrops.db.entities.Folder
import com.readrops.db.entities.Item
import com.readrops.db.entities.account.Account
import org.joda.time.DateTime
import org.koin.core.component.KoinComponent
import org.koin.core.component.get
@ -22,8 +23,9 @@ class NextcloudNewsRepository(
) : BaseRepository(database, account), KoinComponent {
override suspend fun login(account: Account) {
val authInterceptor = get<AuthInterceptor>()
authInterceptor.credentials = Credentials.toCredentials(account)
get<AuthInterceptor>().apply {
credentials = Credentials.toCredentials(account)
}
val displayName = dataSource.login(get(), account)
account.displayedName = displayName
@ -35,11 +37,42 @@ class NextcloudNewsRepository(
): Pair<SyncResult, ErrorResult> = throw NotImplementedError("This method can't be called here")
override suspend fun synchronize(): SyncResult {
return dataSource.synchronize(SyncType.INITIAL_SYNC, NextcloudNewsSyncData()).apply {
insertFolders(folders)
insertFeeds(feeds)
val itemStateChanges = database.newItemStateChangeDao()
.selectItemStateChanges(account.id)
insertItems(items, true)
val starredIds = itemStateChanges.filter { it.starChange && it.starred }
.map { it.remoteId }
val unstarredIds = itemStateChanges.filter { it.starChange && !it.starred }
.map { it.remoteId }
val syncData = NextcloudNewsSyncData(
lastModified = account.lastModified,
readIds = itemStateChanges.filter { it.readChange && it.read }
.map { it.remoteId.toInt() },
unreadIds = itemStateChanges.filter { it.readChange && !it.read }
.map { it.remoteId.toInt() },
starredIds = database.newItemDao().selectStarChanges(starredIds, account.id),
unstarredIds = database.newItemDao().selectStarChanges(unstarredIds, account.id)
)
val syncType = if (account.lastModified != 0L) {
SyncType.CLASSIC_SYNC
} else {
SyncType.INITIAL_SYNC
}
val newLastModified = DateTime.now().millis / 1000L
return dataSource.synchronize(syncType, syncData).apply {
insertFolders(folders)
newFeedIds = insertFeeds(feeds)
insertItems(items, syncType == SyncType.INITIAL_SYNC)
account.lastModified = newLastModified
database.newAccountDao().updateLastModified(newLastModified, account.id)
database.itemStateChangesDao().resetStateChanges(account.id)
}
}

View File

@ -62,38 +62,50 @@ abstract class BaseRepository(
open suspend fun deleteFolder(folder: Folder) = database.newFolderDao().delete(folder)
open suspend fun setItemReadState(item: Item) {
// TODO handle Nextcloud News case
if (account.config.useSeparateState) {
database.newItemStateChangeDao().upsertItemReadStateChange(item, account.id, true)
database.newItemStateDao().upsertItemReadState(
ItemState(
id = 0,
read = item.isRead,
starred = item.isStarred,
remoteId = item.remoteId!!,
accountId = account.id
when {
account.config.useSeparateState -> {
database.newItemStateChangeDao().upsertItemReadStateChange(item, account.id, true)
database.newItemStateDao().upsertItemReadState(
ItemState(
id = 0,
read = item.isRead,
starred = item.isStarred,
remoteId = item.remoteId!!,
accountId = account.id
)
)
)
} else {
database.newItemDao().updateReadState(item.id, item.isRead)
}
account.isLocal -> {
database.newItemDao().updateReadState(item.id, item.isRead)
}
else -> {
database.newItemStateChangeDao().upsertItemReadStateChange(item, account.id, false)
database.newItemDao().updateReadState(item.id, item.isRead)
}
}
}
open suspend fun setItemStarState(item: Item) {
// TODO handle Nextcloud News case
if (account.config.useSeparateState) {
database.newItemStateChangeDao().upsertItemStarStateChange(item, account.id, true)
database.newItemStateDao().upsertItemStarState(
ItemState(
id = 0,
read = item.isRead,
starred = item.isStarred,
remoteId = item.remoteId!!,
accountId = account.id
when {
account.config.useSeparateState -> {
database.newItemStateChangeDao().upsertItemStarStateChange(item, account.id, true)
database.newItemStateDao().upsertItemStarState(
ItemState(
id = 0,
read = item.isRead,
starred = item.isStarred,
remoteId = item.remoteId!!,
accountId = account.id
)
)
)
} else {
database.newItemDao().updateStarState(item.id, item.isStarred)
}
account.isLocal -> {
database.newItemDao().updateStarState(item.id, item.isStarred)
}
else -> {
database.newItemStateChangeDao().upsertItemStarStateChange(item, account.id, false)
database.newItemDao().updateStarState(item.id, item.isStarred)
}
}
}

View File

@ -11,6 +11,7 @@ import com.readrops.db.entities.Folder
import com.readrops.db.entities.Item
import com.readrops.db.entities.ItemState
import com.readrops.db.pojo.ItemWithFeed
import com.readrops.db.pojo.StarItem
import kotlinx.coroutines.flow.Flow
@Dao
@ -60,4 +61,7 @@ abstract class NewItemDao : NewBaseDao<Item> {
@Query("Select case When :guid In (Select guid From Item Inner Join Feed on Item.feed_id = Feed.id and account_id = :accountId) Then 1 else 0 end")
abstract suspend fun itemExists(guid: String, accountId: Int): Boolean
@Query("Select Item.guid, Feed.remoteId as feedRemoteId From Item Inner Join Feed On Item.feed_id = Feed.id Where Item.remoteId In (:remoteIds) And account_id = :accountId")
abstract suspend fun selectStarChanges(remoteIds: List<String>, accountId: Int): List<StarItem>
}