2016-06-11 24 views
8

Trong log4j2 chúng tôi có một tính năng tiện dụng được mô tả nhưKotlin đăng nhập với lambda thông số

// Java-8 style optimization: no need to explicitly check the log level: 
// the lambda expression is not evaluated if the TRACE level is not enabled 
logger.trace("Some long-running operation returned {}",() -> expensiveOperation()); 

nỗ lực của tôi để sử dụng này trong Kotlin

log.debug("random {}", { UUID.randomUUID() }) 

mà sẽ in

random Function0<java.util.UUID> 

Làm cách nào để sử dụng ghi nhật ký đối số lambda với kotlin? Hoặc làm thế nào để chúng tôi nói với kotlin một cách rõ ràng phương thức gọi?

Trả lời

8

Sự cố là debug() bị quá tải và có phương pháp khác lấy đối tượng vararg làm đối số. Kotlin chọn rằng tình trạng quá tải chứ không phải là một tham số Supplier<?> làm đối số, bởi vì nó không biết rằng biểu thức lambda được coi là một Nhà cung cấp.

Chỉ cần xác định nó như là một Nhà cung cấp:

log.debug("random {}", Supplier { UUID.randomUUID() }) 
1

Tôi đã viết một lớp mà làm cho nhiều niềm vui này để sử dụng ... Vì vậy mà chúng ta có thể viết những thứ như

log.debug { "some $thing is $that" } 

đó là tương đương với đăng nhập lambda lười biếng như

log.debug("some {} is {}",()->thing,()->that) 

Bạn thậm chí không cần những {} này cho paramet erising chuỗi, và bạn có tất cả các phương pháp logger gốc vì nó là một đại biểu ...

đây là lớp dành cho những ai muốn sử dụng nó ...

import org.apache.logging.log4j.util.Supplier 

class Logger(private val logger: org.apache.logging.log4j.Logger) : org.apache.logging.log4j.Logger by logger { 

    fun info(supplier:() -> String) { 
     logger.info(Supplier { supplier.invoke() }) 
    } 

    fun debug(supplier:() -> String) { 
     logger.debug(Supplier { supplier.invoke() }) 
    } 

    fun warn(supplier:() -> String) { 
     logger.warn(Supplier { supplier.invoke() }) 
    } 

    fun error(supplier:() -> String) { 
     logger.error(Supplier { supplier.invoke() }) 
    } 

    fun trace(supplier:() -> String) { 
     logger.trace(Supplier { supplier.invoke() }) 
    } 
} 

hoặc nếu bạn muốn để tận dụng các tham chiếu tuyệt vời cho nguồn trong nhật ký, bạn có thể làm

import org.apache.logging.log4j.util.Supplier 

class Logger(val logger: org.apache.logging.log4j.Logger) : org.apache.logging.log4j.Logger by logger { 

    inline fun info(crossinline supplier:() -> String) { 
     logger.info(Supplier { supplier.invoke() }) 
    } 

    inline fun debug(crossinline supplier:() -> String) { 
     logger.debug(Supplier { supplier.invoke() }) 
    } 

    inline fun warn(crossinline supplier:() -> String) { 
     logger.warn(Supplier { supplier.invoke() }) 
    } 

    inline fun error(crossinline supplier:() -> String) { 
     logger.error(Supplier { supplier.invoke() }) 
    } 

    inline fun trace(crossinline supplier:() -> String) { 
     logger.trace(Supplier { supplier.invoke() }) 
    } 
} 
Các vấn đề liên quan