2010-11-26 14 views
2

スケーラの共通のロギングパターンは、具体的なクラス(Liftweb、akkaなどのオープンソースプロジェクトを参照)と混合されたロギング特性を使用することです。そのようなスケーラでロギングの特性を定義するときの問題

何か:

trait Logging { 
    val loggerName = this.getClass.getName 
    @transient lazy val log = new Logger(loggerName) 
} 

これは、私が知る権利を使用しています正確に何ですが、私はこのため、パターンの問題とこだわっています。実際に、ロギング特性が派生したクラスによって混合されている場合、ロガーは最も派生したクラスの名前で使用されます。ここで

は自分自身を明確にする例です。

class Logger(logName : String){ 
    def debug(msg : String) { println("["+logName+"] : "+msg) } 
} 

trait Logging { 
    val loggerName = this.getClass.getName 
    @transient lazy val log = new Logger(loggerName) 
} 

package a { 
    class A extends Logging { 
    log.debug("log from A") 
    } 
} 

package b { 
    import a._ 
    class B extends A with Logging { 
    log.debug("log from B") 
    } 
} 

object LogTest { 
    import b._ 
    def main(args : Array[String]) = { 
    val instance = new B 
    } 
} 

私は私が得たこのプログラムを実行すると:

[b.B] : log from A 
[b.B] : log from B 

の代わりに:

[a.A] : log from A 
[b.B] : log from B 

を誰もが解決策を見つけましたこの問題 ?

+2

しかし、あなたが言っていることは、異なるロガーが欲しいということです: クラスA {val aLog = Logger(classOf [A])} クラスBはA {val bLog = Logger( cl assoo [B])} –

答えて

2

私はコンパニオンオブジェクトでロガーを使用してこの効果を実現できます。

object A extends Logging; 
class A { import A._ 
    log.debug("log from A") 
} 

object B extends Logging; 
class B extends A { import B._ 
    log.debug("log from B") 
} 
+0

これは、 'logging'で' log'が 'protected'とマークされているとき(2.8.1)はコンパイルされません。 [SLF4S](https://github.com/weiglewilczek/slf4s)と[Grizzled-SLF4J](http://software.clapper.org/grizzled-slf4j/)はこれを行い、適切な可視性があると主張したいと思います。おそらく2.8.1のscalacのバグでしょうか? –

-1

これは明白かもしれませんが、あなたはLogging形質が継承したくない場合は、あなたは、単に代わりのプライベート変数を使用することができます形質で混合する。

class A { 
    private val log = Logger(this) 
} 

class B extends A with Logging { 
} 

または

class A extends Logging { 
} 

class B extends A { 
    override lazy val log = // ... 
} 
2

これはほとんど間違いなくあなたがを望む動作ではありませんというのが私の経験です。

あなたはオーバーライドが含まれているいくつかのクラス階層を持っている場合は、あなたのログがのように見えるラインのフルかもしれません:

13:44:42.654 - AbstractFooService [INFO] : I have a: foo 
13:44:42.656 - AbstractFooService [INFO] : I have bar-d my: foo 

そして、あなたは具体的なサービスの実装は、あなたが扱っていたものを自分で尋ねるのだろうか?あなたがわからない場合は、あなたがどこにいるためにどのようなコードパスが使用されたのか、どのように確認できますか?

13:44:42.655 - SpecialFooService [INFO] : I want to baz this foo to bar 

、あなたはすぐにあなたが間違っているのfooを使用しているをを伝えることができるので、ログが

13:44:42.654 - DefaultFooService [INFO] : I have a: foo 
13:44:42.656 - DefaultFooService [INFO] : I have bar-d my: foo 

が含まれている場合、デバッグする方がはるかに簡単:たぶん2わたってるしき寄り添う第三の文があったはずですサービス

関連する問題