1
我想通過JRuby從Java使用ActiveRecord,但是面臨「ClassCastExcecption」問題。從Java使用ActiveRecord時出現奇怪的ClassCastException
該示例應用程序實現如下:
示例/ User.java
package example;
public interface User {
String getName();
}
示例/ UserManager.java
package example;
import java.util.List;
public interface UserManager {
List<User> all_users();
User new_user(String name);
}
user_manager.rb(類路徑中的某處)
require 'rubygems'
require 'arjdbc'
class User < ActiveRecord::Base
include Java::example.User
end
class UserManager
include Java::example.UserManager
def initialize
ActiveRecord::Base.establish_connection(
:adapter => "jdbcsqlite3",
:database => "test.db"
)
end
def new_user(name)
User.new(:name => name)
end
def all_users
User.all
end
end
UserManager.new
示例/ Main.java
package example;
import org.jruby.embed.PathType;
import org.jruby.embed.ScriptingContainer;
public class Main {
public static void main(String[] args) throws Exception {
ScriptingContainer container = new ScriptingContainer();
container.setHomeDirectory("D:/bin/jruby-1.5.6"); // JRuby path
Object userManagerObj = container.runScriptlet(
PathType.CLASSPATH, "user_manager.rb");
UserManager userManager = container.getInstance(
userManagerObj, UserManager.class);
userManager.new_user("Jane Doe"); // (A)
System.out.println("Users:");
for (User user : userManager.all_users()) {
System.out.println(user.getName());
}
}
}
'用戶' 表被事先設置如下:
ActiveRecord::Schema.define do
create_table :users, :force => true do |t|
t.column :name, :string
end
end
User.create(:name => 'John Doe')
當運行上述的主類,一切都很好。
Users:
John Doe
但奇怪的是,如果我將Main.java中的行(A)註釋掉,我得到一個ClassCastException異常。
Users:
Exception in thread "main" java.lang.ClassCastException: org.jruby.RubyObject cannot be cast to example.User
at example.Main.main(Main.java:17)
還可以得到一個ClassCastException - 如果我更新「new_user」的方法來使用類#等效代碼分配如下:
u = User.allocate
u.send :initialize, {:name => name}
u
爲什麼類#新必須提前打電話來避免拋出ClassCastException?我錯過了什麼嗎?
我正在使用JRuby 1.5.6。寶石:
- 的ActiveRecord 3.0.3
- 的ActiveRecord-JDBC適配器1.1.0
- 的ActiveRecord-jdbcsqlite3適配器1.1.0