Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- class ScreenParamsTable @Inject constructor(
- private val db: SupportSQLiteDatabase
- ) {
- init {
- db.execSQL(ScreenParamsModel.CREATE_TABLE)
- db.execSQL(ScreenParamsModel.SCREEN_PARAMS_TYPE_IDX)
- }
- @AutoValue
- internal abstract class ScreenStateParams1 : ScreenParamsModel
- private val creator: Creator<ScreenParamsModel> =
- object : Creator<ScreenParamsModel> by Creator(::AutoValue_ScreenParamsTable_ScreenStateParams1) {}
- private val factory = Factory<ScreenParamsModel>(creator)
- private val mapper = factory.paramsMapper
- private fun SupportSQLiteQuery.queryParams(): DynamicJson =
- db
- .query(this)
- .mapConsume(mapper::map)
- .toParams()
- private fun getRecursiveParamsByType(screen: Screen, type: Int): DynamicJson =
- factory
- .getRecursiveParams(type, screen.id)
- .queryParams()
- private fun getParamsByType(screen: Screen, type: Int): DynamicJson =
- factory
- .getParams(type, screen.id)
- .queryParams()
- private fun getParamByTypes(screen: Screen, vararg types: Int): DynamicJson =
- factory
- .getParamsByTypes(screen.id, types)
- .queryParams()
- private fun getParamsByTypeAndNames(screen: Screen,
- type: Int,
- names: List<String>): DynamicJson =
- factory
- .getParamsByNames(type, screen.id, names.toTypedArray())
- .queryParams()
- private fun getParamByType(screen: Screen, name: String, type: Int): Any? =
- factory
- .getParam(type, screen.id, name)
- .let(db::query)
- .firstConsume(mapper::map)
- ?.let(::extractParam)
- private val addStm = ScreenParamsModel.SetParam(db)
- private val delParamStm = ScreenParamsModel.DeleteParam(db)
- private fun addParams(screen: Screen, params: DynamicJson, paramType: Int) {
- if (params.isEmpty()) return
- db.beginTransaction()
- params.forEach { (name, value) ->
- when(value) {
- null -> delParamStm.exec { bind(paramType, screen.id, name) }
- else -> {
- val (type, stringValue) = packParam(value)
- addStm.exec { bind(screen.id, name, paramType, type, stringValue) }
- }
- }
- }
- db.setTransactionSuccessful()
- db.endTransaction()
- }
- fun getInputAndReturnParams(screen: Screen) = getParamByTypes(screen, PARAM_TYPE_INPUT, PARAM_TYPE_RETURN_BACK)
- fun getNonRecursiveParams(screen: Screen) = getParamByTypes(screen, PARAM_TYPE_INPUT, PARAM_TYPE_STATE, PARAM_TYPE_RETURN_BACK)
- fun setReturnParams(screen: Screen, params: DynamicJson) = addParams(screen, params, PARAM_TYPE_RETURN_BACK)
- fun getStackParam(screen: Screen, name: String) = getParamByType(screen, name, PARAM_TYPE_INPUT_STACK)
- fun getStackParams(screen: Screen) = getRecursiveParamsByType(screen, PARAM_TYPE_INPUT_STACK)
- fun setStackParams(screen: Screen, params: DynamicJson) = addParams(screen, params, PARAM_TYPE_INPUT_STACK)
- fun getInputParams(screen: Screen) = getParamsByType(screen, PARAM_TYPE_INPUT)
- fun setInputParams(screen: Screen, params: DynamicJson) = addParams(screen, params, PARAM_TYPE_INPUT)
- fun getStateParam(screen: Screen, name: String) = getParamByType(screen, name, PARAM_TYPE_STATE)
- fun getStateParams(screen: Screen) = getParamsByType(screen, PARAM_TYPE_STATE)
- fun getStateParamsByNames(screen: Screen, names: List<String>) = getParamsByTypeAndNames(screen, PARAM_TYPE_STATE, names)
- fun setStateParams(screen: Screen, params: DynamicJson) = addParams(screen, params, PARAM_TYPE_STATE)
- fun deleteParamsNotInScreens(screenIds: IntArray) =
- factory
- .deleteParamsNotInScreens(screenIds)
- .let(db::query)
- .close()
- companion object {
- private const val LONG = 1
- private const val STRING = 2
- private const val BOOLEAN = 3
- private const val DOUBLE = 4
- private const val SERIALIZABLE = 5
- private const val LONG_ARRAY = 6
- private const val STRING_ARRAY = 7
- private const val JSON = 9
- private const val PARAM_TYPE_INPUT = 0
- private const val PARAM_TYPE_STATE = 1
- private const val PARAM_TYPE_INPUT_STACK = 2
- private const val PARAM_TYPE_RETURN_BACK = 3
- private const val ARRAY_SEPARATOR = 0.toByte().toChar().toString()
- private val parser = moshiAdapter<Any>()
- private val utf8 = Charset.defaultCharset()
- }
- private fun packParam(value: Any): Pair<Int, String> {
- return when (value) {
- is Int, is Long -> LONG to value.toString()
- is Float, is Double -> DOUBLE to value.toString()
- is String -> STRING to value
- is Boolean -> BOOLEAN to value.toString()
- is Map<*,*> -> JSON to parser.toJson(value)
- is Array<*> -> when {
- value.isArrayOf<String>() -> STRING_ARRAY to value.joinToString(ARRAY_SEPARATOR)
- value.isArrayOf<Long>() -> LONG_ARRAY to value.joinToString(ARRAY_SEPARATOR)
- value.isArrayOf<Serializable>() -> SERIALIZABLE to serialize(value)
- else -> error("Array type not supported $value")
- }
- is Serializable -> SERIALIZABLE to serialize(value)
- else -> error("Param type not supported $value ${value::class.java.canonicalName}")
- }
- }
- private fun List<ScreenParamsModel>.toParams(): DynamicJson {
- val out: MutableDynamicJson = mutableMapOf()
- for (param in this) {
- out[param.name()] = extractParam(param)
- }
- return out
- }
- private fun extractParam(param: ScreenParamsModel): Any? {
- val value = param.value() ?: return null
- return when (param.value_type()) {
- LONG -> value.toLong()
- STRING -> value
- BOOLEAN -> value.toBoolean()
- DOUBLE -> value.toDouble()
- JSON -> parser.fromJson(value) as DynamicJson
- SERIALIZABLE -> deserialize(value)
- STRING_ARRAY -> value
- .takeIf { it.isNotBlank() }
- ?.split(ARRAY_SEPARATOR)
- ?.toTypedArray()
- ?: emptyArray<String>()
- LONG_ARRAY -> value
- .takeIf { it.isNotBlank() }
- ?.split(ARRAY_SEPARATOR)
- ?.map { it.toLong() }
- ?.toTypedArray()
- ?: emptyArray<Long>()
- else -> null
- }
- }
- private fun serialize(obj: Serializable): String {
- val out = ByteArrayOutputStream()
- ObjectOutputStream(out).use {
- it.writeObject(obj)
- it.flush()
- }
- val encoded = Base64.encode(out.toByteArray(), Base64.DEFAULT)
- return encoded.toString(utf8)
- }
- private fun deserialize(obj: String): Any? {
- val decoded = Base64.decode(obj, Base64.DEFAULT)
- return decoded
- .inputStream()
- .let(::ObjectInputStream)
- .use { it.readObject() }
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement