私は社内ライブラリ(作成者がいなくなっている)の回帰テストを作成しており、環境を検証しようとしています。jndi名が「複雑」である場合にのみ、いくつかのテストがそのNameNotFoundExceptionで失敗し続けます。
これはスタンドアロンアプリであり、Webコンテナでは実行されません。アプリは設定ファイルを使用し、LDAPは含まれていません。環境はJavav1.4であり、アプリはローカルに必要なすべてのライブラリとともにインストールされます。(jndi.jar、jms.jarなどのlibディレクトリ)。シンプルでしょ?
ライブラリの複雑さと、ライブラリが多くのオブジェクトをどのように処理するかのために、私は簡単なテストを行い、次に複雑さを増やして、個別のテストとして各部分を追加します。
セットアップ:ファイル:c:\ data \ eclipse \ worksheet \ APP \ testfiles \ jndi \ jms \ label \ .bindings
ファイルには次のエントリーがあります:QReply / FactoryName = com.ibm.mq.jms.MQQueueFactory
UnitTestクラス:「単純な」テストには
Hashtable ht = new Hashtable();
ht.put(Context.PROVIDER_URL,
"file:/data/eclipse/workspace/APP/testFiles/jndi/jms/label/");
ht.put(Context.INITIAL_CONTEXT_FACTORY,
"com.sun.jndi.fscontext.RefFSContextFactory");
ht.put(Context.SECURITY_AUTHENTICATION, "none");
Context ctx;
try {
ctx = new InitialContext(ht);
String jndiName = "QReply";
logger.debug("testFindRemoteObject_Simple",
"Invoking InitialContext.lookup(\"" + jndiName + "\")");
Object remoteObject = ctx.lookup(jndiName);
assertTrue(remoteObject != null);
} catch (NamingException e) {
e.printStackTrace();
fail(e.getMessage());
}
これは合格です。ライブラリで非常に問題があったため、渡された実際のデータと一致する別のテストを作成しました。プロバイダーのURLが短縮され、jndi名が「パス」を取得します。
「実際の」データ単体テスト:
final Hashtable ht = new Hashtable();
ht.put(Context.PROVIDER_URL,
"file:/data/eclipse/workspace/APP/testFiles/jndi/");
ht.put(Context.INITIAL_CONTEXT_FACTORY,
"com.sun.jndi.fscontext.RefFSContextFactory");
ht.put(Context.SECURITY_AUTHENTICATION, "none");
Context ctx;
try {
ctx = new InitialContext(ht);
String jndiName = "jms/label/QReply";
logger.debug("testFindRemoteObject_Actual",
"Invoking InitialContext.lookup(\"" + jndiName + "\")");
Object remoteObject = ctx.lookup(jndiName);
assertTrue(remoteObject != null);
} catch (NamingException e) {
e.printStackTrace();
fail(e.getMessage());
}
失敗する
javax.naming.NameNotFoundException: jms/label/QReply
at com.sun.jndi.fscontext.RefFSContext.getObjectFromBindings(
RefFSContext.java:400)
at com.sun.jndi.fscontext.RefFSContext.lookupObject(RefFSContext.java:327)
at com.sun.jndi.fscontext.RefFSContext.lookup(RefFSContext.java:146)
at com.sun.jndi.fscontext.FSContext.lookup(FSContext.java:127)
at javax.naming.InitialContext.lookup(InitialContext.java:347)
at com.advo.tests.services.UnitTestServiceLocator.testFindRemoteObject_Actual(
UnitTestServiceLocator.java:85)
ここで、UnitTestServiceLocator.java:85はctx.lookup(jndiname);の行です。
単純なテストは成功するのに、より複雑なテストは失敗するのはなぜですか?どちらも、(とりわけ)jmsおよびmqjarが設定されているlibディレクトリを指すクラスパスを使用します。
複雑なテストは、ライブラリが入力する内容と一致しますが、渡される値として魔法を使用します。ライブラリコードには、設定ファイルからマジック値を抽出する「数行」の行があります。私は何が欠けていますか?ライブラリコードはサーバーでは機能しますが、私のラップトップでは失敗します(開発中)。
私は別のjndiパスを作成しました-最初のテストが2番目のテストを台無しにしていた場合に備えて。それでも失敗します。
私には何の欲求も(またはライブラリコードを変更する許可も)ないので、InitialContext(X);を呼び出します。それが図書館がそれを行う方法だからです。InitialContextで何も渡されていない他の例を見てきましたが、なぜそれが優れているのか混乱しています。
更新:Linux java1.5でjndi_testプロジェクトを作成しましたが、失敗したテストは正常に実行されます。同じソースを取得してWindows環境に移動すると、テストは失敗します。LinuxにはCドライブがないが、データファイルは同じであるため、クラスパスにいくつかの変更があります。(うーん区切り文字の問題?)
また、1.5で実行する場合、そのライブラリに問題があることもわかりましたが、それは副次的な問題です。