vendredi 22 février 2019

Get name of enclosing class indirectly

The purpose is to build a "TAG" value, which helps in logging & debugging. Basically when we perform logging we are interesting in the name of the top-level enclosing class, not in used classes nor inner ones to understand the context of an action.

Here is my snippet, which works well with anonymous & inner, but fails on functions with receiver:

class B

class A {

    fun test() {
        B().apply {
            //get "A" string here
            println(TAG)
        }
    }
}

val Any.TAG: String
    get() = getTopLevelClass(this.javaClass).simpleName

private fun getTopLevelClass(clazz: Class<*>): Class<*> =
    clazz.enclosingClass?.let { getTopLevelClass(it) } ?: clazz

It outputs B, which doesn't give me much information about context where it is used

  • I know, it can be achieved with this@A.TAG, but the thing you always should to remember and consider it on writing code, which i want to avoid.
  • I know, it can be done with obtaining stacktrace, but is is very slow and not really trustable source. Logging should be ASAP and not affects an app speed.

So i think this is somehow possible with reflection, java one is preferable to not depends on kotlin-reflection package. The environment is JVM, as i mentioned





Aucun commentaire:

Enregistrer un commentaire