Webrick provides servlet stubs and everything else, so it would be practical, probably trivial, to port IOWA to it.
Here's what I use for Borges, all the work happens in do_GET/do_POST, and the majority of that work is simply mapping WEBrick Request/Response to a Borges request/response. (With a little work, I may be able to use a webrick request/response inside Borges, I haven't looked into it yet.)
require 'webrick' class BorgesServer < WEBrick::HTTPServlet::AbstractServlet attr_accessor :handler def initialize(server, options = {}) super @handler = options[:Handler] || WADispatcher.default end ## # WEBrick HTTP GET handler def do_GET(req, res) request = WARequest.new(req.path, req.header, req.query, req.cookies) response = @handler.handle_request(request) res.status = response.status res.body = response.contents response.headers.each do |k,v| res[k] = v end end ## # WEBrick HTTP POST handler (same as GET) alias do_POST do_GET ## # Create a new Borges Server def self.create(options) options[:BindAddress] ||= '0.0.0.0' options[:Listen] ||= [['::', 7000]] options[:Port] ||= 7000 server = WEBrick::HTTPServer.new(options) server.mount("/borges", BorgesServer, options) return server end ## # Start a new BorgesServer with a SIGINT handler def self.start(options = {}) server = self.create(options) trap("INT") do server.shutdown end server.start return server end end