0

How can I use my main projects layout for my sub apps?

There is a layout option for the controller.. but what would I set the value to in order for it to traverse back into the parent project and use it's application.haml instead?

I tried adding:

File.expand_path('../../app/views/layouts/application.haml', __FILE__)

Unfortunately in the controller it looks like the path of the current apps layouts folder is always added onto the front of it so you end up with something like

c:/sites/demo/app01/views/layouts/c:/sites/demo/app/views/layouts/application.haml

Also, the .haml is already added so if you do add it to the controller you end up with

application.haml.haml

That is only the case for the controller.

Based on those results I moved the code into the sub app.rb, which is actually better for my situation.

However, no main layout is rendered so I only see the results of the current controller action. It doesn't output the layout.

I tried it without the file ext, with etc.. The path being returned is right.. so I'm not sure why it's not using it?

At least in the controller, it was throwing an error because it was an invalid argument.

Having the code in the app.rb for my sub app doesn't produce an error, but it doesn't render the layout either. Just the view result.

Mike
  • 33
  • 3

3 Answers3

0

You can use inside main app or controller:

# in project/parent_app/sub_app/app.rb
layout File.expand_path('../../parent_app/views/application.haml', __FILE__)

this will render:

# project/parent_app/views/application.haml
DAddYE
  • 1,719
  • 11
  • 16
  • the default layout is application, which is what I have right now. however I can't find a way to tell my sub app to use my projects application.haml instead of it's own? when I set the pathing, it always puts my sub apps name in the path. can you show me an example of how you can set the layout path to point to a layout that is sitting in one directory above the current app? – Mike Feb 04 '12 at 15:50
  • 1
    posted results. adding that to controller throws exception. adding it to app.rb of sub app doesn't throw an exception, but only renders the view result. It excludes the layout. – Mike Feb 05 '12 at 06:15
0

I spent a little bit of time to see where the issues were with the controller pre pending the layout with the current applications layout folder when you would specify a abs file path.

file: padrino-core/application/rendering.rb

method: fetch_layout_path

I added the if / else to check to see for an abs file path.

return cached_layout_path if cached_layout_path
if File.exists?(layout_name.to_s)
    layout_path = layout_name.to_sym
else
    has_layout_at_root = Dir["#{views}/#{layout_name}.*"].any?
    layout_path = has_layout_at_root ? layout_name.to_sym : File.join('layouts', layout_name.to_s).to_sym
    end
@_cached_layout[layout_name] = layout_path unless reload_templates?
layout_path

However, it was still erroring out.

file: sinatra-1.3.2/lib/sinatra/base.rb

method: find_template

I added a

yield name.to_s if File.exists?(name.to_s)

right before

yield ::File.join(views, "#{name}.#{@preferred_extension}")

This has worked without any errors.

I'm quite new to ruby and even more so with sinatra / pandrino, so this might not be the right approach, but it works and will allow me to move forward with my current development.

DAddYE: I'd be interested in hearing back from you in regards to a better alternative? I'm not sure why setting the layout in the app.rb of the child application doesn't seem to do anything, I'll try to investigate later.

Mike
  • 33
  • 3
  • I'm hoping you do have an alternative solution to this as the moment I upgrade sinatra or padrino, it's going to break again. I could always fork off github I guess and just keep merging any updates. – Mike Feb 06 '12 at 03:25
0

the fetch_layout_path MUST be relative path. So u should do this in padrino-core/application/rendering.rb:

It's worked for me. But It is not perfect way if padrino allow the nested sub-app.

  def fetch_layout_path(given_layout=nil)
    layout_name = given_layout || @layout || :application
    @_cached_layout ||= {}
    cached_layout_path = @_cached_layout[layout_name]
    return cached_layout_path if cached_layout_path
    has_layout_at_root = Dir["#{views}/#{layout_name}.*"].any?
    layout_path = has_layout_at_root ? layout_name.to_sym : File.join('layouts', layout_name.to_s).to_sym
    # Check the layout file is exists in sub-app? 
    # try to use the root project's layout if not
    # added via riceball
    has_layout = Dir["#{views}/#{layout_path}.*"].any?
    layout_path = has_layout ? layout_path : File.join('..', '..', 'app', 'views', layout_path.to_s).to_sym
    @_cached_layout[layout_name] = layout_path unless reload_templates?
    layout_path
  end
Riceball LEE
  • 1,541
  • 18
  • 18