Loading External JavaScript And CSS Libraries To Lightning Components

ltng:resource is a new Lightning Component that makes it trivial to load 3rd party JavaScript and CSS to a component. This blog shows how to use ltng:resource.

Lightning Components framework provides a great way to easily decompose applications into components. But building applications also depend on tons of other OSS libraries like JQuery, Twitter Bootstrap, Moment.js and more to implement various features.

While loading 3rd party libraries is trivial, loading them into a trusted enterprise environment like Salesforce needs to meet our strict security needs.  They also need to meet various application needs such as loading multiples files in a specific order. So with Spring ‘15 release we created a new component called ltng:require to load libraries while being secure. It has the following features:

  1. Asynchronously load multiple CSS and/or JS libraries

  2. Load libraries in any dependency order the app needs

  3. Let the app know when loading all JS libraries are complete

  4. Most importantly, load only verifiable libraries (for security purposes)

Let’s take at the syntax to better understand it:

 <ltng:require 
 styles="/resource/path/to/css1[,/resource/path/to/css2]" 
 scripts='/resource//path/to/js1.js,[/resource//path/to/js2.js]' 
 afterScriptsLoaded="{!c.controllerFunction}" 
/>
  1. styles – Allows us to specify multiple CSS files separated by comma. They will be loaded from left-to-right.

  2. scripts – Allows us to specify multiple JS files separated by comma. Again they will be loaded from left-to-right

  3. afterScriptsLoaded – Allows us to provide a JS function to notify when all JS files are loaded.

 

Notes:

  1. Files paths must always start from /resource. i.e they must be a static resource to enforce security.

  2. CDNs are not allowed at this point because they are outside of Salesforce data centers and can’t be controlled. In the future, we may allow admins to whitelist CDNs for their orgs.

  3. If you upload a JS or CSS directly into Static resource, then you should reference them by resource name without .css or .js suffix. For example:  /resource/myjsfile or /resource/mycssfile

  4. If your resource is inside a zip file, then you should use .css or .js suffix. For example: /resource/<resourcename>/path/to/myjsfile.js

 

A Bootstrap Dropdown Component Example:

This is a simple wrapper around Twitter Bootstrap’s dropdown menu. This dropdown menu needs 1. JQuery, 2. Bootsrap’s own JS(aka bootstrapjs) and 3. it’s own CSS to work properly. Also it need us to first load JQuery before loading bootstrapjs.

Here is the code to load all three of them:

<ltng:require styles="/resource/bootstrap" scripts='/resource/jquery,/resource/bootstrapjs' afterScriptsLoaded="{!c.jsLoaded}" />

The above code loads bootstrap CSS and JQuery in parallel. And once JQuery is downloaded, it loads bootstrapjs and finally calls “jsLoaded” controller JavaScript function.

dropdown.cmp

<aura:component>
<ltng:require styles="/resource/bootstrap" scripts='/resource/jquery,/resource/bootstrapjs' afterScriptsLoaded="{!c.jsLoaded}" />
<div class='mynamespace'>
	<div class="dropdown">
		<div id="dLabel" type="button" class='btn btn-success' data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
			Some Menu
			<span class="caret"></span>
		</div>
		<ul class="dropdown-menu" role="menu" aria-labelledby="dLabel">
			<li role="presentation"><a role="menuitem" href="">Action</a></li>
			<li role="presentation"><a role="menuitem" href="">Another action</a></li>
		</ul>
	</div>
</div>
</aura:component>

dropdowncontroller.js

({
	jsLoaded: function(component, event, helper) {
		alert('ready to go');
	}
})

Usage or myapp.app

<aura:application>
	<c:dropdown />
</aura:application>

CSS Namespacing:

Many 3rd party CSS libraries like Twitter Bootstrap changes styles for the entire application. This can cause problems when running your component in S1 Mobile app or inside Lightning App Builder. We strongly recommend CSS-namespacing them before using them. This namespace is not the same as your org’s namespace but a simple CSS class name to avoid your CSS bleeding into other components. This could be any unique classname name for a container (div) that wraps your component.

 

For example if your component’s markup is:

<div class=’redColor’> my component </div>

 

And CSS is:

.redColor {color: red}

 

Wrap the markup in another div with a unique class name (say ‘’cssns’)

<div class=’cssns’>
   <div class=’redColor’> my component </div>
</div>

 

And update your CSS file to look like:

.cssns .redColor {
 color: red
}

 

Now, since libraries like Twitter Bootstrap has 1000s of class names, you need to use some tool to namespace all those 1000s of classes like the CSS namespacer tool and use the custom Twitter Bootstrap.

 

CSS Namespacer tool:

https://bootstrap-namespacer.herokuapp.com/ is a simple tool (source) that adds any namespace you want to the entire CSS file.

New to Lightning Components?

There are many resources to get started:

  1. Lightning Components Trailhead (Link):  This provides a simple and fun way to learn Lightning Components. In addition, you’ll acquire badges and points to show off.
  2. Lightning Component Developer Guide (Link) This provides detailed information of everything Lightning Components.
  3. Aura Docs (Link) – This is a built-in lightning app that comes with every org that has Lightning. It provides documentation of every lightning component currently running in that specific org. To open it, simply open /auradocs (https://login.salesforce.com/auradocs) in your org.

 

 

 

 

Leave your comments...

Loading External JavaScript And CSS Libraries To Lightning Components