0 Replies Latest reply on Jun 12, 2006 3:24 PM by rsimonassi

    Dynamic class change/load

    rsimonassi

      Hi,

      I have an application that reads different text files which has different Java codes and create Objects with a method that is dynamicly created from the contents of these text files.

      I have the following architecture of classes:

      public abstract FileScript {

      public abstract void run();

      }

      public Script extends abstract{

      public void run(){
      System.out.println("Script finished!");
      }
      }


      public ScriptFactory{

      ...
      public ScriptFactory getInstance(){

      ...

      }

      private String loadMethodBodyFromFile(String fileName){
      ....
      return methodBody = //loads from filename
      }

      public Script create(String fileName){
      ScriptVO ret = new ScriptVO();
      try{
      String runMethodStr = loadMethodBodyFromFile(scriptFileName);
      ClassPool pool = ClassPool.getDefault();
      CtClass clazz = pool.get("Script");
      CtMethod method = clazz.getDeclaredMethod("run");
      method.insertBefore(runMethodStr);
      Class cl = clazz.toClass();
      ret = (ScriptVO)clazz.toClass(ClassLoader.getSystemClassLoader()).newInstance();

      }catch(Exception exp){
      exp.printStackTrace();
      throw new ScriptException(exp);
      }
      return ret;
      }
      }

      public Test{

      public static void main(String args[]){

      ScriptFactory.getInstance().create("file.txt");
      }

      }

      However I am getting the following error:

      javassist.CannotCompileException: by java.lang.LinkageError: duplicate class definition: Script
      at javassist.ClassPool.toClass(ClassPool.java:813)
      at javassist.ClassPool.toClass(ClassPool.java:765)
      at javassist.CtClass.toClass(CtClass.java:985)
      at ScriptFactory.create(ScriptFactory.java:37)
      at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:650)
      at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:675)
      at java.lang.Thread.run(Thread.java:595)
      Caused by: java.lang.LinkageError: duplicate class definition: br/com/collector/agent/lib/vo/ScriptVO
      at java.lang.ClassLoader.defineClass1(Native Method)
      at java.lang.ClassLoader.defineClass(ClassLoader.java:620)
      at java.lang.ClassLoader.defineClass(ClassLoader.java:465)

      It seems that there is another Script already loaded by my ClassLoader. So, how is it possible to have this kind of dynamic codes with javassist? Should I need user the HotSwapper class? How can I use it?

      Thank you and regards,