Commit Graph
2 Commits
Author SHA1 Message Date
lgcosta 9e0bcc3e9b fix: robustez de sync comprovada no emulador (duplicatas eliminadas)
- ApiClient: IllegalArgumentException de URL vira Network (banner, sem crash);
  DTOs com listas nullable (servidor podia enviar categories/tags: null)
- SyncEngine: mutex global serializa runs (logs BEGIN/END); resolveConflict
  idempotente (não duplica cópia de conflito); registra rekey:<local>→<server>
  em meta para o editor aberto sobreviver à troca de id do create
- ViewModel: resolve(id) em save/delete; createLocal enfileira create único
- Outbox: índice único (noteId, op); DB v2 com fallbackToDestructiveMigration
- proguard: regras corretas de kotlinx.serialization (Companion.serializer)
- README: seção 'Testado em' com os cenários de emulador executados
v0.1.0
2026-11-04 19:28:02 -03:00
lgcosta 2f63c7a2f5 feat: cliente Android offline-first (Kotlin + Jetpack Compose)
- Room (notes/outbox/categories/meta): edição 100% local, fila FIFO de mutações
- SyncEngine bidirecional: push (create/update com base_hash/delete, rekey de id
  local→servidor) + pull (categorias, notas divergentes, exclusões remotas)
- Conflito 409: servidor vence a nota + texto local preservado em cópia
  "Título (conflito)" enfileirada como create — nada perdido, sem relógios
- WorkManager: periódico 1h (rede + backoff exponencial), runNow único REPLACE
  em gatilhos (pós-save, rede restabelecida, boot, config, botão manual)
- OkHttp com timeout/retry em IOException; kotlinx.serialization; DataStore
- UI Compose: tela Servidor (URL+token+teste), Lista com banner de status
  (Offline/Sincronizando/Sincronizado/Erro/401 + pendências + conflitos),
  Editor com autosave por ociosidade (10 s) e categorias multi-seleção
- Build validado: assembleDebug (AGP 8.7.3/Kotlin 2.0.21/SDK 35, JDK 21) —
  app-debug.apk 17,6 MB; gradle-wrapper.jar fora do commit (regenerável com
  `gradle wrapper`, documentado no README)
2026-11-04 17:55:50 -03:00