1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
|
package coffee.liz.rookery
import coffee.liz.rookery.model.Event
import coffee.liz.rookery.model.Penalty
import coffee.liz.rookery.model.Solve
import coffee.liz.rookery.scramble.TnoodleScrambler
import coffee.liz.rookery.store.FolderBlobStore
import coffee.liz.rookery.store.FolderLogStorage
import coffee.liz.rookery.store.Repo
import coffee.liz.rookery.store.Store
import java.nio.file.Files
import kotlin.io.path.appendText
import kotlin.io.path.listDirectoryEntries
import kotlin.test.Test
import kotlin.test.assertEquals
import kotlin.test.assertNotNull
import kotlin.test.assertTrue
class JvmTest {
@Test fun folderSyncBetweenDevicesToleratesTornLines() {
val root = Files.createTempDirectory("rookery-sync")
fun open(node: String) = Repo(Store(node, FolderLogStorage(root, node), FolderBlobStore(root)) { System.currentTimeMillis() })
val a = open("phone")
a.addSolve(Solve("s1", "x", Event.E333, 9000, Penalty.NONE, "R", "", 1))
val b = open("laptop") // fresh device reads everything on startup
assertEquals(listOf("s1"), b.solves().map { it.id })
// simulate Syncthing delivering half of a line from phone
val seg = root.resolve("devices/phone").listDirectoryEntries().single()
val line = """{"t":"9999999999999-0000-phone","c":"solve","id":"s1","f":"pen","v":"dnf"}"""
seg.appendText(line.substring(0, 20))
b.store.sync()
assertEquals(Penalty.NONE, b.solves().single().penalty)
seg.appendText(line.substring(20) + "\n")
b.store.sync()
assertEquals(Penalty.DNF, b.solves().single().penalty)
// restart: state rebuilds from disk
assertEquals(Penalty.DNF, open("laptop").solves().single().penalty)
val blob = a.store.blobs.put(byteArrayOf(1, 2, 3), "jpg")
assertEquals(3, open("laptop").store.blobs.get(blob)?.size)
}
/** Runs under the app's 256m heap cap (see core/build.gradle.kts), so this also guards memory. */
@Test fun tnoodleScramblesAndDraws() {
val s = TnoodleScrambler()
for (e in Event.entries) {
val scr = s.next(e)
assertTrue(scr.isNotBlank(), "$e")
val svg = assertNotNull(s.previewSvg(e, scr), "$e svg")
assertTrue(svg.contains("<svg"), "$e svg: ${svg.take(80)}")
}
}
}
|