### Question:
JRubyRackInput extends RubyObject { @JRubyMethod(optional = 1) public IRubyObject read(ThreadContext context, IRubyObject[] args) { Integer length = null; if (args.length > 0) { long arg = args[0].convertToInteger("to_i").getLongValue(); length = (int) Math.min(arg, Integer.MAX_VALUE); } try { return toRubyString(rackInput.read(length)); } catch (IOException e) { throw getRuntime().newIOErrorFromException(e); } } JRubyRackInput(Ruby runtime, RubyClass klass);  JRubyRackInput(Ruby runtime, RackInput rackInput); @JRubyMethod IRubyObject gets(); @JRubyMethod IRubyObject each(ThreadContext context, Block block); @JRubyMethod(optional = 1) IRubyObject read(ThreadContext context, IRubyObject[] args); @JRubyMethod IRubyObject rewind();  }### Answer:
@Test public void shouldWrapJavaIOExceptions() throws Exception { Ruby ruby = Ruby.newInstance(); RackInput rackInput = mock(RackInput.class); when(rackInput.read(null)).thenThrow(new IOException("fake")); JRubyRackInput subject = new JRubyRackInput(ruby, rackInput); GlobalVariables globalVariables = ruby.getGlobalVariables(); globalVariables.set("$rack_input", subject); IRubyObject result = ruby.evalScriptlet( "begin; $rack_input.read; rescue IOError => e; \"rescued #{e.message}\"; end"); assertThat(result.asJavaString()).isEqualTo("rescued fake"); }