2012-06-08 29 views
1

另一个类我有两个项目:一个分析器和一个基本的应用程序(使用JUnit测试)装载用Javassist

探查器使用了Javassist仪器的基本应用。

当分析器位于基本应用程序中时,它工作正常。 当探查器在基本应用程序之外时,我必须将基本应用程序jar文件导入Eclipse上的构建路径,以便能够检测我的应用程序。

我想对我的命令行基本的应用程序运行我的探查为EMMA做:罐子profiler.jar application.jar运行

但我不

的java不知道如何告诉我的分析器,好的,用这个罐子来测试。

这里是我的探查主要代码:

public static void main(String[] args) throws Exception { 
    Loader loader = new Loader(); 
    loader.addTranslator(ClassPool.getDefault(), new Profiler()); 
    try { 
     loader.run("com.application.bookstore.test.Test", null); 
    } catch (Throwable e) { 
     e.printStackTrace(); 
    } 
} 

我想这样做:

final String arg = args[0]; 
final String[] commandArgs = new String[args.length - 1]; 
System.arraycopy(args, 1, commandArgs, 0, commandArgs.length-1); 

loader.run(arg, commandArgs); 

但是当我运行它,我得到:

[[email protected] build]$ java -jar profiler.jar bookstore.jar 
java.lang.ClassNotFoundException: bookstore.jar 
    at java.net.URLClassLoader$1.run(URLClassLoader.java:217) 
    at java.security.AccessController.doPrivileged(Native Method) 
    at java.net.URLClassLoader.findClass(URLClassLoader.java:205) 
    at java.lang.ClassLoader.loadClass(ClassLoader.java:321) 
    at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:294) 
    at java.lang.ClassLoader.loadClass(ClassLoader.java:266) 
    at javassist.Loader.delegateToParent(Loader.java:429) 
    at javassist.Loader.loadClass(Loader.java:315) 
    at java.lang.ClassLoader.loadClass(ClassLoader.java:266) 
    at javassist.Loader.run(Loader.java:289) 
    at com.modeln.Profiler.main(Profiler.java:93) 

所以,我想直接运行到我的Main类目录中:

[[email protected] test]$ ls 
profiler.jar Test.class 
[[email protected] test]$ java -jar profiler.jar Test 
java.lang.NoClassDefFoundError: Test (wrong name: com/application/bookstore/test/Test) 
    at java.lang.ClassLoader.defineClass1(Native Method) 
    at java.lang.ClassLoader.defineClass(ClassLoader.java:634) 
    at java.lang.ClassLoader.defineClass(ClassLoader.java:480) 
    at javassist.Loader.findClass(Loader.java:380) 
    at javassist.Loader.loadClass(Loader.java:312) 
    at java.lang.ClassLoader.loadClass(ClassLoader.java:266) 
    at javassist.Loader.run(Loader.java:289) 
    at com.modeln.Profiler.main(Profiler.java:93) 

所以你有任何想法如何运行我的分析器外部jar项目?非常感谢!

回答

1

好吧,这里的解决方案:只要pool.insertClassPath()

public static void main(String[] args) throws Exception { 
    Loader loader = new Loader(); 
    loader.addTranslator(ClassPool.getDefault(), new Profiler()); 
    try { 
     if (args.length < 1) { 
      System.out.println(TOOL_USAGE); 
     } else { 

      //Initialize profiler with config/config.properties file 
      initializeProfiler(); 

      final String[] commandArgs = new String[args.length - 1]; 
      System.arraycopy(args, 1, commandArgs, 0, commandArgs.length); 

      //Open a jar file, unJar it into /tmp/ then add the /tmp/ classpath to the javassist laoder 
      File file = new File(args[0]); 
      JarFile jarFile = new JarFile(args[0]); 
      Manifest manifest = jarFile.getManifest(); 
      String mainClassName = null; 

      if (manifest != null) { 
       mainClassName = manifest.getMainAttributes().getValue("Main-Class"); 
      } 

      jarFile.close(); 

      mainClassName = mainClassName.replaceAll("/", "."); 
      //Default temp directory is Jarfilename without .jar 
      final File workDir = File.createTempFile(args[0].substring(0, args[0].indexOf('.')), ""); 
      workDir.delete(); 
      workDir.mkdirs(); 

      //Unjar all files into WorkDir temp directory 
      unJar(file, workDir); 

      //Add all directories into classPath 
      createClassPath(workDir, file); 

      //Add the classPath with unJar files into the Javassist ClassPool 
      ClassPool pool = ClassPool.getDefault(); 
      pool.insertClassPath(workDir + "/"); 
      loader.run(mainClassName, null); 

      } 

    } catch (Throwable e) { 
     e.printStackTrace(); 
    } 

    System.out.println("Instrumentation of " + args[0] + " finished."); 
}