how to override a gem's views

I’m trying to override the main layout but the gem is actually using other gems together as a group so there’s a separate gem for vendor Within the vendor gem can be found app/views but within my main app the question is what should the path to overrides be vendor/app/views or app/views/vendor

When a gem is mounted, its internal paths are mounted into the regular Rails lookup paths, but importantly, they are not looked at first in the lookup process. You can read the Rails Guide about Layouts and Rendering to learn more about this process: https://guides.rubyonrails.org/layouts_and_rendering.html#finding-layouts

When a controller in the gem calls "render", explicitly or implicitly, Rails will first look in the app's views directory to find that template or layout or partial. Only if it does not find it there will it look in the gem. I don't think that the vendor directory even comes into play here.

The easiest way to figure this out is to look at the internal layout of the gem on GitHub. Tell us which one you're using, and this can be figured out quite easily. For example, here is a gem that provides views:

https://github.com/rubysherpas/forem

Click into the app/views directory, and you'll see two directories: forem and layouts/forem. These directories are going to be "projected" into the parent Rails app's app/views directory. You won't see them, but Rails will act as though they are there.

If you wanted to override a view provided in either of those directories, say, layouts/forem/default.html.erb, all you would need to do in your app is to create a folder named app/views/forem, and put a file named default.html.erb in it. Whatever you put in that file in your app will be loaded whenever the gem requests the same-named file, and the file that was in the gem itself will be ignored. Rails always loads and uses the first file it finds. This is by design, so an app can override a gem if desired.

Walter

Thanks Walter spree_frontend-3.6.6

Okay, so you are trying to mount a replacement for something in spree/frontend/app/views/spree/layouts. To shadow over that path from your app, you will want to make a new directory at [your_project]/app/views/spree/layouts. Put whichever replacement layout file you want in that folder, and that's it -- no step three.

Walter

Why is frontend omitted from the path ?

>
>
>
> I'm trying to override the main layout but the gem is actually using other gems together as a group so there's a separate gem for vendor Within the vendor gem can be found app/views but within my main app the question is what should the path to overrides be vendor/app/views or app/views/vendor
>
> Thanks Walter spree_frontend-3.6.6

Okay, so you are trying to mount a replacement for something in spree/frontend/app/views/spree/layouts. To shadow over that path from your app, you will want to make a new directory at [your_project]/app/views/spree/layouts. Put whichever replacement layout file you want in that folder, and that's it -- no step three.

Walter

Why is frontend omitted from the path ?

Look at the paths again. Wherever you find 'app' is the pivot point for the paths. From the point of view of the template lookup system, that's the "you are here". Everything to the left of that will not be present in the lookup. Everything to the right of that is part of the resource path. This same principle works for other lookups, too; it's not restricted to view templates. Controllers, models, helpers -- anything your app needs and a gem might provide -- are all referenced this same way.

Walter

Thanks