feat: Add PENDING_DELETE filter to all paginated queries and implement accordion-style drawer navigation
- Add sync_status != 'PENDING_DELETE' condition to all PagingSource queries in LinkDao (getAllLinksPaged, searchLinks, searchLinksFullText, getLinksByTag, getLinksByMultipleTags, getLinksInCollectionPaged, getDeadLinks, getPinnedLinksPaged) - Update LinkRepositoryImpl to exclude PENDING_DELETE items in dynamic query builder and multi-tag filtering - Replace independent drawer accordion states
This commit is contained in:
parent
b9efb14b8d
commit
e742502bdc
@ -25,7 +25,7 @@ interface LinkDao {
|
||||
@Query("SELECT * FROM links ORDER BY is_pinned DESC, created_at DESC")
|
||||
fun getAllLinks(): Flow<List<LinkEntity>>
|
||||
|
||||
@Query("SELECT * FROM links ORDER BY is_pinned DESC, created_at DESC")
|
||||
@Query("SELECT * FROM links WHERE sync_status != 'PENDING_DELETE' ORDER BY is_pinned DESC, created_at DESC")
|
||||
fun getAllLinksPaged(): PagingSource<Int, LinkEntity>
|
||||
|
||||
@Query("SELECT * FROM links WHERE id = :id")
|
||||
@ -41,9 +41,10 @@ interface LinkDao {
|
||||
|
||||
@Query("""
|
||||
SELECT * FROM links
|
||||
WHERE title LIKE '%' || :query || '%'
|
||||
WHERE sync_status != 'PENDING_DELETE'
|
||||
AND (title LIKE '%' || :query || '%'
|
||||
OR description LIKE '%' || :query || '%'
|
||||
OR url LIKE '%' || :query || '%'
|
||||
OR url LIKE '%' || :query || '%')
|
||||
ORDER BY is_pinned DESC, created_at DESC
|
||||
""")
|
||||
fun searchLinks(query: String): PagingSource<Int, LinkEntity>
|
||||
@ -52,6 +53,7 @@ interface LinkDao {
|
||||
SELECT links.* FROM links
|
||||
INNER JOIN links_fts ON links.id = links_fts.rowid
|
||||
WHERE links_fts MATCH :query
|
||||
AND links.sync_status != 'PENDING_DELETE'
|
||||
ORDER BY links.is_pinned DESC, links.created_at DESC
|
||||
""")
|
||||
fun searchLinksFullText(query: String): PagingSource<Int, LinkEntity>
|
||||
@ -59,6 +61,7 @@ interface LinkDao {
|
||||
@Query("""
|
||||
SELECT * FROM links
|
||||
WHERE tags LIKE '%' || :tag || '%'
|
||||
AND sync_status != 'PENDING_DELETE'
|
||||
ORDER BY is_pinned DESC, created_at DESC
|
||||
""")
|
||||
fun getLinksByTag(tag: String): PagingSource<Int, LinkEntity>
|
||||
@ -66,6 +69,7 @@ interface LinkDao {
|
||||
@Query("""
|
||||
SELECT * FROM links
|
||||
WHERE tags LIKE '%' || :tag1 || '%' AND tags LIKE '%' || :tag2 || '%'
|
||||
AND sync_status != 'PENDING_DELETE'
|
||||
ORDER BY is_pinned DESC, created_at DESC
|
||||
""")
|
||||
fun getLinksByMultipleTags(tag1: String, tag2: String): PagingSource<Int, LinkEntity>
|
||||
@ -80,6 +84,7 @@ interface LinkDao {
|
||||
SELECT links.* FROM links
|
||||
INNER JOIN collection_links ON links.id = collection_links.link_id
|
||||
WHERE collection_links.collection_id = :collectionId
|
||||
AND links.sync_status != 'PENDING_DELETE'
|
||||
ORDER BY links.is_pinned DESC, collection_links.added_at DESC
|
||||
""")
|
||||
fun getLinksInCollectionPaged(collectionId: Long): PagingSource<Int, LinkEntity>
|
||||
@ -103,6 +108,7 @@ interface LinkDao {
|
||||
@Query("""
|
||||
SELECT * FROM links
|
||||
WHERE link_check_status = 'BROKEN'
|
||||
AND sync_status != 'PENDING_DELETE'
|
||||
ORDER BY last_health_check DESC
|
||||
""")
|
||||
fun getDeadLinks(): PagingSource<Int, LinkEntity>
|
||||
@ -152,7 +158,7 @@ interface LinkDao {
|
||||
@Query("SELECT * FROM links WHERE is_pinned = 1 ORDER BY created_at DESC")
|
||||
fun getPinnedLinks(): Flow<List<LinkEntity>>
|
||||
|
||||
@Query("SELECT * FROM links WHERE is_pinned = 1 ORDER BY created_at DESC")
|
||||
@Query("SELECT * FROM links WHERE is_pinned = 1 AND sync_status != 'PENDING_DELETE' ORDER BY created_at DESC")
|
||||
fun getPinnedLinksPaged(): PagingSource<Int, LinkEntity>
|
||||
|
||||
// ====== Sync ======
|
||||
|
||||
@ -79,7 +79,7 @@ constructor(
|
||||
} else {
|
||||
val whereClause = tags.joinToString(" AND ") { "tags LIKE ?" }
|
||||
val sql =
|
||||
"SELECT * FROM links WHERE $whereClause ORDER BY is_pinned DESC, created_at DESC"
|
||||
"SELECT * FROM links WHERE sync_status != 'PENDING_DELETE' AND $whereClause ORDER BY is_pinned DESC, created_at DESC"
|
||||
val args: Array<Any> = tags.map { "%\"$it\"%" }.toTypedArray()
|
||||
linkDao.getLinksByTags(SimpleSQLiteQuery(sql, args))
|
||||
}
|
||||
@ -420,7 +420,7 @@ constructor(
|
||||
// ====== Helpers ======
|
||||
|
||||
private fun buildFilteredQuery(filter: com.shaarit.domain.model.BookmarkFilter): PagingSource<Int, LinkEntity> {
|
||||
val conditions = mutableListOf<String>()
|
||||
val conditions = mutableListOf<String>("sync_status != 'PENDING_DELETE'")
|
||||
val args = mutableListOf<Any>()
|
||||
|
||||
// Time-based filters
|
||||
|
||||
@ -318,10 +318,8 @@ fun FeedScreen(
|
||||
val reminderViewModel: com.shaarit.presentation.reminders.ReminderViewModel = hiltViewModel()
|
||||
val linkIdsWithReminders by reminderViewModel.linkIdsWithReminders.collectAsState()
|
||||
|
||||
// États des accordéons du drawer
|
||||
var mainMenuExpanded by remember { mutableStateOf(true) }
|
||||
var collectionsExpanded by remember { mutableStateOf(true) }
|
||||
var tagsExpanded by remember { mutableStateOf(true) }
|
||||
// États des accordéons du drawer (accordion: un seul ouvert à la fois)
|
||||
var expandedSection by remember { mutableStateOf("main") }
|
||||
|
||||
// Set initial tag filter
|
||||
LaunchedEffect(initialTagFilter) { viewModel.setInitialTagFilter(initialTagFilter) }
|
||||
@ -404,8 +402,8 @@ fun FeedScreen(
|
||||
// Navigation principale - Accordéon
|
||||
AccordionSection(
|
||||
title = "MENU PRINCIPAL",
|
||||
expanded = mainMenuExpanded,
|
||||
onToggle = { mainMenuExpanded = !mainMenuExpanded },
|
||||
expanded = expandedSection == "main",
|
||||
onToggle = { expandedSection = if (expandedSection == "main") "" else "main" },
|
||||
modifier = Modifier.padding(top = 8.dp)
|
||||
) {
|
||||
Column(
|
||||
@ -493,8 +491,8 @@ fun FeedScreen(
|
||||
// Types de contenu - Accordéon
|
||||
AccordionSection(
|
||||
title = "TYPES DE CONTENU",
|
||||
expanded = true,
|
||||
onToggle = { },
|
||||
expanded = expandedSection == "content",
|
||||
onToggle = { expandedSection = if (expandedSection == "content") "" else "content" },
|
||||
modifier = Modifier.padding(vertical = 4.dp)
|
||||
) {
|
||||
Column(
|
||||
@ -633,8 +631,8 @@ fun FeedScreen(
|
||||
// Collections rapides - Accordéon
|
||||
AccordionSection(
|
||||
title = "COLLECTIONS",
|
||||
expanded = collectionsExpanded,
|
||||
onToggle = { collectionsExpanded = !collectionsExpanded },
|
||||
expanded = expandedSection == "collections",
|
||||
onToggle = { expandedSection = if (expandedSection == "collections") "" else "collections" },
|
||||
trailingContent = {
|
||||
TextButton(
|
||||
onClick = {
|
||||
@ -699,8 +697,8 @@ fun FeedScreen(
|
||||
// Tags populaires - Accordéon
|
||||
AccordionSection(
|
||||
title = "TAGS POPULAIRES",
|
||||
expanded = tagsExpanded,
|
||||
onToggle = { tagsExpanded = !tagsExpanded },
|
||||
expanded = expandedSection == "tags",
|
||||
onToggle = { expandedSection = if (expandedSection == "tags") "" else "tags" },
|
||||
trailingContent = {
|
||||
TextButton(
|
||||
onClick = {
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
<#
|
||||
<#
|
||||
.SYNOPSIS
|
||||
Script de build et de versioning pour ShaarIt.
|
||||
.DESCRIPTION
|
||||
|
||||
@ -1,3 +1,3 @@
|
||||
#Thu Feb 12 09:29:54 2026
|
||||
VERSION_NAME=1.2.0
|
||||
VERSION_CODE=8
|
||||
#Thu Feb 12 10:28:52 2026
|
||||
VERSION_NAME=1.2.3
|
||||
VERSION_CODE=11
|
||||
Loading…
x
Reference in New Issue
Block a user