Styling for multi tenant rails api apps - ruby-on-rails

I have a rails-api app where I'd like to serve a stylus stylesheet with some variables set based on the current tenant.
The main app itself is a static, standalone RIA built in Dojo and doesn't make use of the Rails asset pipeline.
The stylesheet however, I'd like to have sprockets assemble from various sources as well as some values from the database.
Goals/desires:
I'd like to start out with a stylesheet in app/assets/stylesheets
I'd like the stylesheet in app/assets/stylesheets to include a base stylesheet that's distributed as part of the standalone RIA app found in public/ria/src/namespace/resources/base.styl
I'd like to be able to run the stylesheet in app/assets/stylesheets through ERB to populate it with some variables based on the current tenant
Ideally sprockets would cache the result of this process per-tenant
Important note:
I bootstrap the application with a simple static HTML file in /public. The RIA is in effect server agnostic and is a simple git module checked out into the public dir.

Related

Can I share my CSS with another application when using asset pipeline?

I am using Rails asset pipeline in a rails 4.x web app. In production I use a CDN (cloudfront) to serve the CSS.
My other application is a non-rails app, but it shares the same CSS as my Rails app.
Is there a way for my other application to use the CSS generated by my rails application?
The problem I am having is that since rails generates a random guid for the filename there is no way for me to reference it in my other application.
e.g.
https://abcd.cloudfront.net/assets/application-asdf23409usdflu34uasdf.css
Update
If I can get the value I can potentially expose the CSS URL as an API endpoint, is that possible?
When you deploying your application and precompiling assets, the task also generates a manifest-md5hash.json that contains a list with all your assets and their respective fingerprints. It looks like:
{"files":{"application-723d1be6cc741a3aabb1cec24276d681.js":{"logical_path":"application.js","mtime":"2013-07-26T22:55:03-07:00","size":302506, "digest":"723d1be6cc741a3aabb1cec24276d681"}, etc...}
You can transfer this file to another application and get correct filenames with guids from it.

Spree application and main rails application CSS loading

I have a Spree application and some pages that are not part of the spree application. My problem is that styles are shared between those pages. (they look similar, but they have their own asset locations)
How do I do it so I don't have to maintain two sets of stylesheets/JS files?
Just extract common stylesheets to separate CSS files then include them in your applications:
use build process (such as Asset Pipeline)
symlinks (not a best way but I think it will works too)
submodules (if you are using Git)
put common stylesheets to separate gem and use it as part of Asset Pipeline (like any Rails gems with assets inside)

Why can't I add a plain link tag in Rails4 App

Why is it so forbidden to add line like <link href="/assets/stylesheets/bootstrap/bootstrap.css" rel="stylesheet"> in my application.html.erb file. How else do I insert it?
It's not "forbidden" outright - it just skirts a lot of important Rails conventions which will likely create problems & inconsistencies down the line
There are several elements to what you're asking. Here they are:
Layout
Firstly, you need to use the correct helpers in your layout:
#app/views/layout/application.html.erb
<%= stylesheet_link_tag "bootstrap/bootsrap" %>
The reason for this is the same as using helpers in other parts of your Rails application - as paths change between environments & certain "backend" functionalities of the system evolve, you can't rely on using vanilla HTML to call "Rails-centric" methods
A pro tip is that if there is any reference to a path, or an asset, you need to use the helpers which Rails provides
Asset Pipeline
Further to this, you need to appreciate how the "asset pipeline" works.
One of the big benefits of the Rails framework is that it gives you the ability to organize your assets in the most effective way - by keeping them in the /assets folder.
Whilst great for development, your problem will arise when you go into a production environment - Rails prefers to serve static assets in production, which means that the assets will be pre-compiled & access in the public folder:
In the production environment Sprockets uses the fingerprinting scheme
outlined above. By default Rails assumes assets have been precompiled
and will be served as static assets by your web server.
To make sure this works properly, you need to use the path helpers to load the files dynamically; hence allowing Rails to access the files wherever they are on the system
--
Manifest
I would strongly recommend you look into the "manifest" feature of the asset pipeline:
#app/assets/stylesheets/application.css
/*
*= require bootstrap/bootstrap
*/

Angular ui bootstrap custom templates in Rails

How can I use the custom templates of angular ui bootstrap in rails?
I mean, if I use pagination for example it will look for a templates/pagination/pagination.html template.
The problem is that rails won't serve templates in that path, it actually needs to be assets/templates/pagination/pagination.html using the <%= asset_path(....) %> helper.
Hacking the angular ui bootstrap javascript file is a way, but I don't feel like hacking it every time I get a new version.
What I would suggest is to bundle custom templates with the library itself or inside a separate file. The technique to use is to fill in $templateCache with the content of your custom templates. Have a look at one of the files distributed with tamplates to see what I mean:
https://github.com/angular-ui/bootstrap/blob/gh-pages/ui-bootstrap-tpls-0.3.0.js#L2042
You can bundle templates into the $templateCache as part of the build process or prepare this file manually (in this case you need to write templates as JS strings).
Downloading individual templates via XHR for each and every directive would be wasteful as it would result in many XHR requests and would slow down your application. Also, if you preload templates into the $templateCache you can specify required path, one that doesn't need to be a valid path on your WWW server.
I use bower to manage my js libs.
Hence I have these files in my vendor/assets/javascripts/ folder:
angular-ui/bootstrap-bower
With these files, you can simply require them in your javascript manifest file (usually application.js)
//= require angular-bootstrap/ui-bootstrap
//= require angular-bootstrap/ui-bootstrap-tpls
and then you don't need to specify any templates if you want to use the default built-in templates.
I find this solution in the following url
Ref:angular-ui-bootstrap-directive-template-missing

Understanding the Rails 3 Directory Structure

I've found several sites online that explain the DIR structure of a Rails app, but I'm still not clear on a few, mainly:
/vendor
/lib
/public
What should go where? I want to know the best practice. For example, I have jQuery plugins, should those be located in /vendor? /public? /lib? I've read all 3 from different sites online.
Thanks
Vendor is third party code / libraries, so, yes, a good place for jQuery plugins.
Public is for static assets, stuff that gets no benefit from being in the asset pipeline.
Lib is generally used to contain your code that is not specific to the app. i.e. stuff you use in multiple apps. There is a trend to put domain logic in lib e.g. domain classes not based on ActiveModel. Gary Bernhardt (https://www.destroyallsoftware.com/) is a proponent of this.
Typically the contents of /public are directly served by the web server (nginx, apache etc.) without intervention from rails, so traditionally all of your static assets (images, stylesheets, javascripts etc.) went in here. You can still put your javascript in there but it's a bit old fashioned.
Rails 3.1 introduced the asset pipeline which changed all of this. Assets in app/assets, lib/assets and vendor/assets all get servers up by the asset pipeline. Normally your application specific assets would go in app/assets and 3rd party libraries (such as a query plugin) would go in vendor/assets. If you were developing your own set of jquery plugins you might put them in lib/assets. Assets will 'work' no matter where you put them though - it's just a question of organisation.
Gems can also have their own asset folders, for example the jquery-rails gem bundles jquery and allows your app to serve up jquery without actually copying it into your app. I find this even neater than putting things in vendor/assets.

Resources