From: Sys Ppp Date: 2009-08-27T05:01:26+09:00 Subject: Rack must not dictate how to create a middleware In current realization of Rack::Builder the method :use dictates that middlewares must be instances of some class by internal invoking :new initializer. Thus Rack's Builder demands to delegate creation of middleware object and demands existing special class for middleware. Though in most cases middleware conforms with singleton pattern. Or just simply a callable object. Moreover, it is always more cleary to link already existing middleware, created outside of builder. Is middleware worse than ordinary app in respect of this? :) Unneeded delegation of creation makes unneeded coupling and unneeded restrictions. As Vidar Hokstad well wrote in his post "Cohesion vs. coupling" http://www.hokstad.com/why-coupling-is-always-bad-cohesion-vs-coupling.html Looking at realization of Builder's methods we can make something like this. # first variant module MiddleHello # this method needs only # to prevent duplicating of code in second example def self.invoke app, env, who, whom status, header, resp = app.call env add_str = "" if resp.kind_of? Rack::Response new_resp = Rack::Response.new(add_str, status, header) new_resp.write resp.body return new_resp.finish end [status, header, (add_str + resp)] end def self.creator app @app = app self end def self.call env invoke @app, env, self.method(:call), "#{self.class}: #{self}" end end # second variant middle_hello = proc do |app| proc do |env| # just for preventing duplication of code MiddleHello.invoke app, env, Proc, Proc end end builder = Rack::Builder.new do use ... ....... use ... map '/some_path' do run MiddleHello.method(:creator) # :run instead of :use ! run middle_hello # :run instead of :use ! run OurApp end end It works. Now I can not find better solution without changing of Builder class. But it looks like a hack. First. There are no warranties that realization of Builder's methods will not have changed in the future. Second. It is still needed an additional object for creating a middleware object. Third, and maybe more important. This breaks the semantics of Builder's language. And it is losing distinction in declarations of middlewares and ordinary apps. Of course we can remake the Builder or make a subclass from it. But can it cause conflicts with hostings where Rack is used for administration? -- Posted via http://www.ruby-forum.com/.