脚本java:从外部文件导入类

时间:2010-06-22 13:27:19

标签: java scripting mozilla rhino jdk1.6

我想导入一个我已在外部文件夹中编写的类, 例如 : 我的班级Example.java位于c:\class\Example.java我的脚本中,如使用

var importedClass = new JavaImporter("c:\\class\\Example.java");

importClass("c:\\class\\Example.java");

这是ScriptEngine rhino的脚本 我该怎么办?

3 个答案:

答案 0 :(得分:5)

我明白你想:

  1. 编译Java源文件
  2. 加载已编译的代码
  3. 在某些JavaScript中使用结果类
  4. javax.tools包提供了一种编译代码的机制,但是如果你没有在JDK中运行,ToolProvider.getSystemJavaCompiler()将返回null,你将不得不依赖其他一些代码。编译机制(调用外部编译器;嵌入Eclipse编译器等)。

    Java字节码(.class二进制文件)可以在运行时通过ClassLoader加载。

    为了使加载的类对脚本引擎可见,您需要通过ScriptEngineManager(ClassLoader)构造函数提供它们。


    编辑:根据要求

    public class HelloWorld {
      public void say() {
        System.out.println("Hello, World!");
      }
    }
    

    此脚本只调用Java反射API从HelloWorld.class目录加载并实例化类C:\foo\bin

    function classImport() {
      var location = new java.net.URL('file:/C:/foo/bin/');
      var urlArray = java.lang.reflect.Array.newInstance(java.net.URL, 1);
      urlArray[0] = location;
      var classLoader = new java.net.URLClassLoader(urlArray);
      return classLoader.loadClass("HelloWorld");
    }
    
    var myClass = classImport();
    
    for(var i=0; i<10; i++) {
      myClass.getConstructor(null).newInstance(null).say();
    }
    

    我确信有更优雅的方法可以做到这一点。

答案 1 :(得分:1)

我会质疑为什么这样做。

此处列出的解决方案可行。问题是:

  1. 你将有一个鹅卵石拼凑在一起 具有反射的解决方案 很难排除故障。
  2. 您的客户是否还好 修补加载的代码 运行 ?我工作的每个地方 at at not。

答案 2 :(得分:0)

如果我理解正确,你实际上要做的是加载Java类,以便(可能)创建实例,等等。这个术语是动态加载而不是导入。

Java允许您使用*.class方法动态加载字节码文件(ClassLoader.loadClass(String))。这个主题有很多资源;例如JNDI教程中的“Class Loading”页面。准备好花点时间了解这个话题。特别是,由于您正在尝试加载不在应用程序的正常类路径上的类,因此您需要创建一个新的类加载器来执行此操作。 java.lang.ClassLoader类的Javadoc是here

Java源代码不能直接加载,但必须首先使用Java编译器进行编译。如果您使用的是现代JDK安装,则可以在运行时调用Java编译器。但是JRE安装不包括Java编译器。如果您的平台在运行时具有可用的Java编译器,则可以通过ToolProvider类的getSystemJavaCompiler()静态方法访问它。再一次,从正在运行的Java应用程序中调用Java编译器很复杂。