2012-04-25 7 views
4

私は、これがうまくいかないという脳死の愚かなことをしなければならないことを知っていますが、実行中のサーバに動作を動的にロードしたい状況にあります。 。私はこれを行うための私のツールとしてグルーヴィーを選んだ。この振る舞いは、私のモデルオブジェクトやFreemarkerのようなサードパーティのライブラリなど、サーバのクラスパス上のクラスを参照する必要があります。Javaに埋め込まれたGroovy

私はこの愚かなPOCを一緒に投げて実行可能性を示しました。 GroovyClassPathの親クラスパスを自分の現在のものに設定しているにもかかわらず、Javaクラス "ThingyDoodle"と "Fooable"を解決するための素晴らしいスクリプトを手に入れることはできません。

public class GroovyTest 
{ 
    public static void main (String [ ] argv) throws Throwable 
    { 
      // Setting parent classloader! 
      // also tried plain old "GroovyTest.class.getClassLoader()" as well 
     GroovyClassLoader gcl = new GroovyClassLoader (Thread.currentThread().getContextClassLoader()) ; 
     String src = 
       "class Arf implements Fooable { 
       public String foo () { 
        return new ThingyDoodle().doStuff('Arf');}}" ; 
     Class clazz = gcl.parseClass(src, "AppleSauce.groovy"); 
     Object aScript = clazz.newInstance(); 
     Fooable myObject = (Fooable) aScript; 
     System.out.println (myObject.foo()) ; 
    } 

    public static interface Fooable { public String foo () ; } 

    public static class ThingyDoodle 
    { 
     public String doStuff (String input) 
     { 
      return "Hi Worlds" ; 
     } 
    } 
} 

ここで間違っているのは何ですか?

Exception in thread "main" org.codehaus.groovy.control.MultipleCompilationErrorsException: startup failed: 
AppleSauce.groovy: 1: unable to resolve class Fooable 
@ line 1, column 1. 
    class Arf implements Fooable { public String foo () { return new ThingyDoodle().doStuff('Arf');}} 
^

AppleSauce.groovy: 1: unable to resolve class ThingyDoodle 
@ line 1, column 63. 
    ublic String foo () { return new Thingy 
            ^

答えて

3

あなたのコードの問題は、FooableインターフェイスとThingyDoodleクラスが両方とも内部的なので見つけることができませんlクラスを含み、包含クラス名で修飾する必要があります。つまり、GroovyTestです。私は組み込みスクリプトの両方の名前を修飾し(そしてスクリプトの引用符を修正しました)、期待どおりに実行しました。

import groovy.lang.GroovyClassLoader; 

public class GroovyTest 
{ 

    public static void main (String [ ] argv) throws Throwable 
    { 
      // Setting parent classloader! 
      // also tried plain old "GroovyTest.class.getClassLoader()" as well 
     GroovyClassLoader gcl = new GroovyClassLoader (Thread.currentThread().getContextClassLoader()) ; 
     String src = 
       "class Arf implements GroovyTest.Fooable { " + 
       "public String foo () { " + 
        "return new GroovyTest.ThingyDoodle().doStuff('Arf');}}" ; 
     Class clazz = gcl.parseClass(src, "AppleSauce.groovy"); 
     Object aScript = clazz.newInstance(); 
     Fooable myObject = (Fooable) aScript; 
     System.out.println (myObject.foo()) ; 
    }  
    public static interface Fooable { public String foo () ; } 

    public static class ThingyDoodle 
    { 
     public String doStuff (String input) 
     { 
      return "Hi Worlds" ; 
     } 
    } 


} 
+0

さて、それは恥ずかしかったです:) – billmill

+0

ありがとうございました!これが私の必要なものです。 – billmill

+2

汗を流さないでください。私は他の人に欠陥[バグ]を発見することに優れていますが、私自身の[バグ]には盲目です.... – Nicholas

2

ないあなたがそれをコンパイルしているか確認してください...私は(ビルド・ツールとしてGradleを使用して)これを試してみました、それが動作します...

apply plugin:'application' 

repositories { 
    mavenCentral() 
} 

dependencies { 
    compile group: 'org.codehaus.groovy', name: 'groovy', version: '1.8.6' 
} 

mainClassName = 'org.timyates.GroovyTest' 
./build.gradle

./src/main/java/org/timyates/Fooable.java

package org.timyates ; 

public interface Fooable { 
    public String foo() ; 
} 

./src/main/java/org/timyates/ThingyDoodle.java

package org.timyates ; 

public class ThingyDoodle { 
    public String doStuff(String input) { 
    return String.format("Hi %s", input) ; 
    } 
} 

./src/main/java/org/timyates/GroovyTest.java

package org.timyates ; 

import groovy.lang.GroovyClassLoader ; 

public class GroovyTest { 
    public static void main(String[] args) throws Exception { 
    GroovyClassLoader gcl = new GroovyClassLoader(GroovyTest.class.getClassLoader()) ; 
    String src = "import org.timyates.*\n" + 
       "class Arf implements Fooable {\n" + 
       " public String foo() {\n" + 
       " new ThingyDoodle().doStuff('tim')\n" + 
       " }\n" + 
       "}" ; 
    Class clazz = gcl.parseClass(src, "AppleSauce.groovy") ; 
    Fooable myObject = (Fooable)clazz.newInstance() ; 
    System.out.println(myObject.foo()) ; 
    } 
} 

その後、私はコマンドラインでgradle runを入力すると、私は出力を得る:

$ gradle run 
:compileJava 
:processResources UP-TO-DATE 
:classes 
:run 
Hi tim 

BUILD SUCCESSFUL 
+0

実行時にJ2EEサーバー内でインラインでコンパイルしています。もし私がgradleを使用するなら、それはこの練習の目的を破るでしょう。とにかくありがとう! – billmill

+0

十分に良い、嬉しい、それはソートされています:-)質問にそのような情報を入れておくと、次回の時間を節約できます;-)幸い! –

関連する問題