Details
-
Type:
Bug
-
Status:
Resolved
-
Priority:
Major
-
Resolution: Fixed
-
Affects Version/s: JRuby 1.6.7
-
Fix Version/s: JRuby 1.7.0.pre2
-
Component/s: Java Integration
-
Labels:None
-
Number of attachments :
Description
On Windows it picks .submit(Runnable):
Z:\ssl>jruby --version
jruby 1.6.7 (ruby-1.8.7-p357) (2012-02-22 3e82bc8) (Java HotSpot(TM) Client VM 1.7.0_04) [Windows Server 2008 R2-x86-java]
Z:\ssl>jruby method_choosing_bug.rb
opening connection to example.com...
opened
<- "GET / HTTP/1.1\r\nAccept: */*\r\nHost: example.com\r\n\r\n"
Conn close because of error can't convert nil into String
TypeError: can't convert nil into String
concat at org/jruby/RubyString.java:2485
rbuf_fill at method_choosing_bug.rb:12
readuntil at c:/jruby-1.6.7/lib/ruby/1.8/net/protocol.rb:116
readline at c:/jruby-1.6.7/lib/ruby/1.8/net/protocol.rb:126
read_status_line at c:/jruby-1.6.7/lib/ruby/1.8/net/http.rb:2026
read_new at c:/jruby-1.6.7/lib/ruby/1.8/net/http.rb:2015
request at c:/jruby-1.6.7/lib/ruby/1.8/net/http.rb:1051
__file__ at method_choosing_bug.rb:23
start at c:/jruby-1.6.7/lib/ruby/1.8/net/http.rb:543
(root) at method_choosing_bug.rb:23
On Linux it's .submit(Callable):
$ jruby --version jruby 1.6.7 (ruby-1.8.7-p357) (2012-02-22 3e82bc8) (OpenJDK 64-Bit Server VM 1.6.0_23) [linux-amd64-java] $ jruby method_choosing_bug.rb opening connection to example.com... opened <- "GET / HTTP/1.1\r\nAccept: */*\r\nHost: example.com\r\n\r\n" -> "HTTP/1.0 302 Found\r\n" -> "Location: http://www.iana.org/domains/example/\r\n" -> "Server: BigIP\r\n" -> "Connection: Keep-Alive\r\n" -> "Content-Length: 0\r\n" -> "\r\n" reading 0 bytes... -> "" read 0 bytes Conn keep-alive #<Net::HTTPFound 302 Found readbody=true>
Well, there's a bit of an issue here...which one is the "right" one to call? They're both equally valid, since all we have to go on is that you have a block of code you want to pass to submit. They're being chosen differently on different systems because they're coming out of JDK's reflection logic in different orders, and they both "match".
One way to get around this would be to use a small explicit implementation of the interface you see, like this:
class RunnableProc
{ block body }include java.lang.Runnable
def initialize(&block)
@block = block
end
def run; block.call; end
end
...
executor.submit(RunnableProc.new
)
There may be a way to disambiguate these calls without using a concrete class, too. I need to poke around a bit.