Skip to content

Instantly share code, notes, and snippets.

@KaustubhPatange
Last active December 26, 2020 14:35
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save KaustubhPatange/089792e18c19783247bb5b554e4ccaee to your computer and use it in GitHub Desktop.
Save KaustubhPatange/089792e18c19783247bb5b554e4ccaee to your computer and use it in GitHub Desktop.
Mapping a data class to another data class typically found in the apps which follows clean architecture (domain, etc.)
/**
* If there is two same classes like below one maybe domain & other may be entity
* Following method might help to map such instance to other classes.
*
* This is done completely through reflection by matching parameters name.
*
* [convertType] This can be used to transform intermediate values if their types are different in other.
*/
inline fun <reified F : Any, reified T : Any> mapToClass(from: F, convertType: (String, Any?) -> Any? = { _,v -> v }): T {
val args = HashMap<KParameter, Any?>()
val params: List<KParameter> = T::class.constructors.first().parameters
F::class.memberProperties.forEach { prop: KProperty1<out F, Any?> ->
if (prop.visibility == KVisibility.PUBLIC) {
val kParam: KParameter = params.first { it.name == prop.name }
val value: Any? = prop.getter.call(from)
args[kParam] = convertType.invoke(kParam.name!!, value)
}
}
return T::class.constructors.first().callBy(args)
}
@KaustubhPatange
Copy link
Author

Example usage

data class Setting(
   val isSettings1: Boolean,
   val computeMathExp: List<String>,
   val episodeNum: Int
)

@Entity // Example Room
data class SettingDb(
   val isSettings1: Boolean,
   val computeMathExp: String,
   val episodeNum: Int
)

val setting = Setting(...)
val settingsDb: SettingDb = mapToClass(setting) { p, v ->
   // Use this callback to transform data from one type to another eg: computeMathExp
   if (p == Setting::computeMathExp.name) {
       return@call (v as List<String>).joinToString()
   }
   return@call v                                               
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment