2011-02-03 97 views
1

使用JRuby 1.6.0RC1的JRuby +沒有公共構造

我有一個像

package com.foo.bar 

public class Foo 
{ 
Foo(String baz){} 
} 

如果在JRuby中,我做

com.foo.bar.Foo.new "foo" 

然後我得到

的Java文件
TypeError: no public constructors for Java::ComFooBar::Foo 

閱讀http://jira.codehaus.org/browse/JRUBY-5009讓我這是WAD的事情,但我如何解決這個問題而不改變java文件?

子類的Foo然後實例我得到一個不同的錯誤:

ArgumentError: Constructor invocation failed: tried to access method com.foo.bar.Foo.(Ljava/lang/String;)V from class org.jruby.proxy.com.foo.bar.Foo$Proxy0

編輯:

得到它的幫助下,通過從Headius工作在IRC上。下面的作品,但也可能會被更智能:

def package_local_constructor klass,*values 
    constructors = klass.java_class.declared_constructors 
    constructors.each do |c| 
     c.accessible = true 
     begin 
     return c.new_instance(*values).to_java 
     rescue TypeError 
     false 
     end 
    end 
    raise TypeError,"found no matching constructor for " + klass.to_s + "(" + value.class + ")" 
    end 

回答

0

在Java中,你可以使用反射API做這樣的事情:

Constructor constructor = MyClass.class.getConstructor(Class ... paramTypes); 
constructor.setAccessible(true); 
MyClass myClass = (MyClass)constructor.newInstance(Object ... args); 

不知道你能做到這一點在JRuby中,但我想象你可以。

有一個oracle引導這個:http://download.oracle.com/javase/tutorial/reflect/member/ctorInstance.html

+0

這遠非一個完整的解決方案,但它是最接近我,所以我會接受它的人的。 – yxhuvud 2011-02-07 11:49:04

3

有確實沒有公共構造了點。構造函數是包級別。

怎麼做這類型的包com.foo.bar獲取對象以外的其他Java類?可能是該包中已有一個工廠通過調用包範圍構造函數來生成此類,並且您可以從JRuby調用。

如果沒有,你可以做一個公共工廠類在包,可能在Java中,有可能在Ruby中,並從那裏調用此構造。

您可能還能夠猴子補丁添加紅寶石訪問的構造函數或工廠方法,而無需修改Java源代碼。

相關問題