|
|
@@ -1,10 +1,7 @@ |
|
|
|
package me.jfenn.gitrest.service |
|
|
|
|
|
|
|
import kotlinx.serialization.ImplicitReflectionSerializer |
|
|
|
import kotlinx.serialization.KSerializer |
|
|
|
import kotlinx.serialization.builtins.list |
|
|
|
import kotlinx.serialization.serializer |
|
|
|
import kotlinx.serialization.serializerOrNull |
|
|
|
import kotlinx.serialization.* |
|
|
|
import kotlinx.serialization.builtins.ListSerializer |
|
|
|
import me.jfenn.gitrest.model.GitrestConfig |
|
|
|
import me.jfenn.gitrest.provider.gitea.model.GiteaUser |
|
|
|
import java.io.File |
|
|
@@ -24,7 +21,7 @@ class DiskCache( |
|
|
|
|
|
|
|
fun String.cacheFile() = File(cacheDir, "${this.replace(File.separator, "_")}.json") |
|
|
|
|
|
|
|
@ImplicitReflectionSerializer |
|
|
|
@InternalSerializationApi |
|
|
|
override suspend fun set(key: String, value: Any) { |
|
|
|
// obtain a serializer + type for the value (this is all just a ridiculous hack) |
|
|
|
val serializer: KSerializer<Any> |
|
|
@@ -32,7 +29,7 @@ class DiskCache( |
|
|
|
if (value is List<*>) { |
|
|
|
// GiteaUser is just a default list hack for when the list is empty; it's never actually serialized in this case |
|
|
|
val type = value.firstOrNull()?.let { it::class } ?: GiteaUser::class |
|
|
|
serializer = type.serializer().list as KSerializer<Any> |
|
|
|
serializer = ListSerializer(type.serializer()) as KSerializer<Any> |
|
|
|
typeName = "list:${type.java.name}" |
|
|
|
} else { |
|
|
|
serializer = value::class.serializerOrNull() as KSerializer<Any> |
|
|
@@ -40,7 +37,7 @@ class DiskCache( |
|
|
|
} |
|
|
|
|
|
|
|
// add type + expiration metadata before serializing |
|
|
|
val string = typeName + "#" + System.currentTimeMillis() + "#" + config.jsonSerializer.stringify(serializer, value) |
|
|
|
val string = typeName + "#" + System.currentTimeMillis() + "#" + config.jsonSerializer.encodeToString(serializer, value) |
|
|
|
|
|
|
|
try { |
|
|
|
cacheDir.mkdirs() |
|
|
@@ -50,7 +47,7 @@ class DiskCache( |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
@ImplicitReflectionSerializer |
|
|
|
@InternalSerializationApi |
|
|
|
override suspend fun <T> get(key: String): T? { |
|
|
|
return try { |
|
|
|
// check contents; destructure file parts if safe |
|
|
@@ -60,12 +57,12 @@ class DiskCache( |
|
|
|
|
|
|
|
// obtain the correct serializer for {className} |
|
|
|
val serializer = if (className.startsWith("list:")) |
|
|
|
Class.forName(className.substring(5)).kotlin.serializer().list as KSerializer<Any> |
|
|
|
ListSerializer(Class.forName(className.substring(5)).kotlin.serializer()) as KSerializer<Any> |
|
|
|
else Class.forName(className).kotlin.serializer() as KSerializer<Any> |
|
|
|
|
|
|
|
// parse JSON if before expiry date; else return null for default behavior (fetch the actual request) |
|
|
|
if (System.currentTimeMillis() - lastModified.toLong() < cacheDuration) { |
|
|
|
config.jsonSerializer.parse(serializer, json) as? T |
|
|
|
config.jsonSerializer.decodeFromString(serializer, json) as? T |
|
|
|
} else null |
|
|
|
} catch (e : IOException) { |
|
|
|
config.logError("GIT-REST: ${e::class.simpleName} - ${e.message}") |
|
|
|