2017-03-27 5 views
0

かなり奇妙な問題があります。作成後にJavaファイルロガーがハイジャックされ、別のロガーに属するファイル(Gigaspaces APIから)にリダイレクトされる

Logger.getLogger()、FileHandle、およびSimpleFormatterを使用して標準Javaロガーを作成しました。 これらは正常に動作し、期待どおりにログファイルを出力します。

次に、独自のログを含むGigaspaces API(com.gigaspaces.gs-openspaces - Maven依存関係を介して含まれる)からいくつかのクラスを使用しました。 その後、私のロガーのすべての出力はGigaspacesログファイル(例えば、〜/ .m2/repository/com/gigaspaces/logs/2017-03-27〜12.46-gigaspaces-service-135.60.146.142-23534 .log)ではなく、適切なログファイルを使用する必要があります。

私はGigaspacesを初期化した後でさらにロガーを作成すると、これらの新しいロガーは期待どおりに動作します。ギガパスを初期化する前に作成されたロガーのみが影響を受けます。

私はGigaspacesのコードをちょっと調べてみましたが、そこにはたくさんのコードがあります。私はただちに何も見えなかった。

私のロガーの設定に何か問題がありますか?ライブラリがそのクラスに無関係な既存のロガーからの出力を盗むことができるようには思われません。

以下の短いテストプログラムは、問題を示しています。

Logger testLog = Logger.getLogger("testlog"); 
    try { 
     FileHandler fh = new FileHandler("testlog.log"); 
     fh.setFormatter(new SimpleFormatter()); 
     testLog.addHandler(fh); 
    } 
    catch (Exception e) { 
     // Not important 
     e.printStackTrace(); 
    } 

    testLog.log(Level.INFO, "This appears in the main log file"); 

    // Spin up gigaspaces, even by trying to connect to a space that doesn't exist 
    UrlSpaceConfigurer testSpaceConfigurer = new UrlSpaceConfigurer("jini://*/*/testSpace?locators=127.0.01").lookupTimeout(1); 
    try { 
     GigaSpace g = new GigaSpaceConfigurer(testSpaceConfigurer).gigaSpace(); 
    } 
    catch (Exception e) { 
     // This will throw an exception, just ignore it. 
    } 
    testSpaceConfigurer.close(); 

    testLog.log(Level.INFO, "This appears in the (wrong) gigaspaces log file"); 
+1

GigaSpacesは、デフォルトで、他のサービスからのフレームワークへのロギングをリダイレクトする別のロギングフレームワーク(log4j、logbackなど)を使用していると思います。 – john16384

+0

私はチェックしましたが、log4jやその他のフレームワークに依存していないようです。それは、(Avalon)LogKitに推移的な依存関係があります。私はMavenを通してそれを除外しようとしましたが、それは何の違いもありませんでした。 –

答えて

0

jmehrensが示唆しているように、セキュリティマネージャをオーバーライドする方法があるようです。 私は以下のようなものを、それをLogManagerのオン・リセット()メソッドを実行する権限を拒否することによって、ロギングを盗むからGigaspacesを止めることができました:

// Silly hack to keep gigaspaces from STEALING ALL OUR LOGS 
static { 
    System.setSecurityManager(new SecurityManager() { 
     @Override 
     public void checkPermission(Permission p) { 
      if (p instanceof LoggingPermission) { 
       for (StackTraceElement stackTraceElement : new Exception().getStackTrace()) { 
        if (stackTraceElement.getMethodName().equalsIgnoreCase("reset") && stackTraceElement.getClassName().equalsIgnoreCase("java.util.logging.LogManager")) { 
         throw new SecurityException("No resetting the logger! It is forbidden."); 
        } 
       } 
      } 
     } 
    }); 
} 

私はこの場合、私はちょうどの静的ブロック内のオーバーライドを追加しました私のgigaspaceのインスタンスを作成するクラスですが、初期化する前にどこでも実行する必要があります。

0

あなたはpin the "testlog" loggerに持っているか、あなたがそれに適用される変更のすべてを失う危険性があります。

ロガーを変更するには、アクセス許可が必要です。 1つの選択肢は、GigaSpacesがログをリダイレクトできないカスタムセキュリティマネージャを使用することです。

GigaSpacesがLogManager.reset()を呼び出す場合、ハンドラを取り除くためにハックして、臭いがあり、汚い方法の1つは、FileHandlerを拡張してequalsを上書きすることです。

public class GigaSpaces { 

    //Pin the logger 
    private static final Logger testLog = Logger.getLogger("testlog"); 
    static { 
     try { 
      FileHandler fh = new FileHandler("testlog.log") { 
       public boolean equals(Object o) { 
        return false; //Pure Evil. 
       } 
      }; 

      fh.setFormatter(new SimpleFormatter()); 
      testLog.addHandler(fh); 
     } 
     catch (Exception e) { 
      // Not important 
      e.printStackTrace(); 
     } 
    } 

    public void foo() throws Throwable { 
     testLog.log(Level.INFO, "This appears in the main log file"); 

     // Spin up gigaspaces, even by trying to connect to a space that doesn't exist 
     UrlSpaceConfigurer testSpaceConfigurer = new UrlSpaceConfigurer("jini://*/*/testSpace?locators=127.0.01").lookupTimeout(1); 
     try { 
      GigaSpace g = new GigaSpaceConfigurer(testSpaceConfigurer).gigaSpace(); 
     } 
     catch (Exception e) { 
      // This will throw an exception, just ignore it. 
     } finally { 
      testSpaceConfigurer.close(); 
     } 

     testLog.log(Level.INFO, "This appears in the (wrong) gigaspaces log file"); 
    } 
} 
関連する問題