Add interruption/atomicity, SFTP, and scheduling tests
Build & Release APK / build (push) Successful in 12m50s
Build & Release APK / build (push) Successful in 12m50s
- Interruption: failed mid-write leaves original intact (no truncation, no temp leftover); a sync that drops after N files resumes cleanly on the next sync with all content byte-intact (real network-drop simulation). - SFTP: live round-trip test against an SFTP server (connect/upload-atomic/ list/download/overwrite/special-name/delete); skips if endpoint unreachable. - Scheduling: WorkManager request builders map Wi-Fi-only -> UNMETERED, charging-only -> requiresCharging, interval, input data, and tags correctly.
This commit is contained in:
@@ -0,0 +1,47 @@
|
||||
package com.syncflow
|
||||
|
||||
import androidx.test.ext.junit.runners.AndroidJUnit4
|
||||
import androidx.work.NetworkType
|
||||
import com.syncflow.worker.SyncWorker
|
||||
import org.junit.Assert.assertEquals
|
||||
import org.junit.Assert.assertFalse
|
||||
import org.junit.Assert.assertTrue
|
||||
import org.junit.Test
|
||||
import org.junit.runner.RunWith
|
||||
import java.util.concurrent.TimeUnit
|
||||
|
||||
/**
|
||||
* Scheduling/constraint mapping for WorkManager-backed syncs. Verifies the request builders
|
||||
* translate pair settings into the right constraints (Wi-Fi-only, charging-only), interval, input
|
||||
* data, and tags — the deterministic part of scheduling (without waiting for the OS to fire it).
|
||||
*/
|
||||
@RunWith(AndroidJUnit4::class)
|
||||
class SchedulingTest {
|
||||
|
||||
@Test fun periodic_wifiOnly_chargingOnly_intervalAndData() {
|
||||
val req = SyncWorker.buildPeriodicRequest(pairId = 42L, intervalMinutes = 30, wifiOnly = true, chargingOnly = true)
|
||||
val ws = req.workSpec
|
||||
assertEquals(NetworkType.UNMETERED, ws.constraints.requiredNetworkType)
|
||||
assertTrue("charging constraint", ws.constraints.requiresCharging())
|
||||
assertEquals(TimeUnit.MINUTES.toMillis(30), ws.intervalDuration)
|
||||
assertEquals(42L, ws.input.getLong(SyncWorker.KEY_PAIR_ID, -1))
|
||||
assertTrue("sync_42" in req.tags)
|
||||
}
|
||||
|
||||
@Test fun periodic_anyNetwork_noCharging() {
|
||||
val req = SyncWorker.buildPeriodicRequest(pairId = 7L, intervalMinutes = 60, wifiOnly = false, chargingOnly = false)
|
||||
val c = req.workSpec.constraints
|
||||
assertEquals(NetworkType.CONNECTED, c.requiredNetworkType)
|
||||
assertFalse(c.requiresCharging())
|
||||
}
|
||||
|
||||
@Test fun oneTime_constraintsDataAndTag() {
|
||||
val req = SyncWorker.buildOneTimeRequest(pairId = 9L, wifiOnly = true, chargingOnly = false, silent = true)
|
||||
val ws = req.workSpec
|
||||
assertEquals(NetworkType.UNMETERED, ws.constraints.requiredNetworkType)
|
||||
assertFalse(ws.constraints.requiresCharging())
|
||||
assertEquals(9L, ws.input.getLong(SyncWorker.KEY_PAIR_ID, -1))
|
||||
assertTrue(ws.input.getBoolean(SyncWorker.KEY_SILENT, false))
|
||||
assertTrue("sync_9" in req.tags)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user