-
Notifications
You must be signed in to change notification settings - Fork 43
Description
Background: Sinatra 1.4.5, Erector 0.10.0, Ruby 2.1.2
I'm using Erector in a Sinatra app. Rather than creating a Tilt registration for Erector, I decided to just declare some Widgets in other ruby files:
require 'rubygems'
require 'erector'
module MySinatraApp
class FooWidget < Erector::Widget
def content
# bla bla
end
end
endThen I require the widget in my main sinatra application, and when I want to render a FooWidget, I make an instance of it and to_html it:
require 'rubygems'
require 'sinatra'
require_relative 'views/foo_widget.rb'
module MySinatraApp
class App < Sinatra::Base
get '/' do
FooWidget.new.to_html
end
end
endNow what I want to do is invoke Sinatra helpers in the body of the FooWidget. For example, I might have some CSS file in my FooWidget, being linked to via some path /css/app.css. But this might fail if my app was actually hosted at example.com/myapp. I want to use the to helper instead. So somehow, I need to get the to helper into the widget.
The heart of the problem (at least it looks that way to me) is that the to helper has to be evaluated in the context of the sinatra app instance, so my current solution is to wrap the helper in a Proc and pass it to the widget like this:
# in the Sinatra app
get '/' do
FooWidget.new(:to => Proc.new { |url| to url }).to_html
end
# in FooWidget
def content
link :rel => stylesheet, :href => @to.call('/css/app.css')
endThis seems to work. I'd definitely call it an ugly hack though. Is there a better or clever-er way? I'm willing to restructure the widget and where it fits into my application, if that enables a better solution.