方便的Kotlin LoggerFactory简化

时间:2018-01-02 10:54:55

标签: android logging kotlin slf4j slf4j-api

使用kotlin使用SLF4J或其他日志记录方法最方便的方法是什么?

通常开发人员忙于像

这样的样板代码
private val logger: Logger = LoggerFactory.getLogger(this::class.java)

在每个班级中获得一个合适的记录器?

使用Kotlin统一/简化此操作的最方便方法是什么?

5 个答案:

答案 0 :(得分:2)

您可以在每种类型上定义扩展属性:

val <T : Any> T.logger: Logger
    get() = LoggerFactory.getLogger(this::class.java)

按如下方式使用:

class X {
    init {
        logger.debug("init")
    }
}

答案 1 :(得分:1)

我在我的项目中定义了这个函数,以便为我更轻松地定义记录器。它利用了Kotlin的具体类型。

// Defined in Utilities.kt
inline fun <reified T:Any> logFor() =
    LoggerFactory.getLogger(T::class.java)

用法:

class MyClass {
    private val log = logFor<MyClass>()
    ...
 }

或者如果你创造了很多:

class MyClass {
    companion object {
        private val log = logFor<MyClass>()
    }
    ...
}

答案 2 :(得分:1)

这是一个简单的示例,它从绑定的可调用引用或标准属性返回一个延迟初始化的记录器。我更喜欢从可调用引用调用,因为::表示反射(与日志记录相关)。

提供Lazy<Logger>的小组:

class LoggingProvider<T : Any>(val clazz: KClass<T>) {

  operator fun provideDelegate(inst: Any?, property: KProperty<*>) =
      lazy { LoggerFactory.getLogger(clazz.java) }
}

调用它们的内联函数:

inline fun <reified T : Any> KCallable<T>.logger() = 
  LoggingProvider(T::class)

inline fun <reified T : Any> T.logger() = 
  LoggingProvider(T::class)

以下是使用它们的示例。初始值设定项中的require断言显示记录器共享一个引用:

class Foo {

  val self: Foo = this

  val logger by this.logger()
  val callableLogger by this::self.logger()

  init {
    require(logger === callableLogger)
  }

}

答案 3 :(得分:0)

如果你不喜欢样板文件,你总是可以用你自己的记录器帮助器包裹log.info

mylog.info(this, "data that needs to be logged")

然后在后台,有一些hashmap跟踪可以为该类实例化记录器的this param的类。

其他选项可能是使用AspectJ Weaving将记录器编织到每个类中,但在我看来这是过度的。

答案 4 :(得分:-2)

我为此

定义了一个实用工具方法
fun getLogger(cl: KClass<*>): Logger {
    return LoggerFactory.getLogger(cl.java)!!
}

现在在每个班级我都可以像这样使用记录器

companion object {
    private val logger = getLogger(MyClass::class)
}