Introducing WebJars – Web Libraries as Managed Dependencies
Update: I’ve created a Spring MVC WebJars example.
Update 2: Ukrainian translation here – http://softdroid.net/vvedennya-webjars by Eclipse Android.
Our web apps are using more and more web libraries like jQuery, Backbone.js and Twitter Bootstrap. The traditional way to use those libraries is to locate & download the JavaScript and CSS source then just copy it into a project. To me this resembles how we used to just copy JAR files into a project’s WEB-INF/lib dir. But why not do with web libraries like we now do with Java libraries and specify them as managed dependencies? This allows us to declaratively set the version, use a consistent version across an application, and easily deal with transitive dependencies. Then we just need web frameworks that can serve static assets from JAR files and we are good to go! Luckily Play 2 and Dropwizard both have out-of-the-box support for this. So I decided to give it a try…
I packaged up some JavaScript and CSS web libraries into JARs, put them into a Maven repo and it worked! And thus the WebJars project was born!
Lets look at an example for how to use the Twitter Bootstrap WebJar in a Play 2 app. First we need to add the WebJars Maven repo to the Play 2 dependency resolvers and specify Bootstrap as a dependency. For Play 2 this is done in the “project/Build.scala” file. Here is one for my Play 2 WebJars Demo project:
import sbt._ import Keys._ import PlayProject._ object ApplicationBuild extends Build { val appName = "play2_webjars_demo" val appVersion = "1.0-SNAPSHOT" val appDependencies = Seq( "com.github.twitter" % "bootstrap" % "2.0.2" ) val main = PlayProject(appName, appVersion, appDependencies, mainLang = JAVA).settings( resolvers += "webjars" at "http://webjars.github.com/m2" ) }
Now to use Bootstrap in a Scala template, we can just do:
<link rel='stylesheet' media='screen' href='@routes.Assets.at("stylesheets/bootstrap.min.css")'>The “@routes.Assets.at” thing just gets a reverse route for the URL that will serve the “bootstrap.min.css” file from the Bootstrap WebJar. Note: It’s not necessary in Play 2 to use the reverse routing but it is a type safe way to get a URL. Based on the default routes in Play 2 the route to that file will be “/assets/javascripts/bootstrap.min.js” which we could have used instead.
Now here is the super cool part… The Bootstrap WebJar depends on jQuery so now I can also just use jQuery:
<script type='text/javascript' src='@routes.Assets.at("javascripts/jquery.min.js")'></script>That is super simple and now I’m managing my web libraries as dependencies!
Note: Play 2 actually puts a copy of jQuery in the default project template but hopefully for Play 2.1 they will pull it out and instead use the jQuery WebJar. In my demo project I’ve removed that copy of jQuery because it’s no longer needed.
If you want to use WebJars with Dropwizard then first setup the Maven “pom.xml” file with the WebJars repo and add the dependency:
<repositories> <repository> <id>webjars</id> <url>http://webjars.github.com/m2</url> </repository> </repositories> <dependencies> <dependency> <groupId>com.github.twitter</groupId> <artifactId>bootstrap</artifactId> <version>2.0.2</version> </dependency> </dependencies>
Then add an “AssetBundle” that will serve static assets in the “public” directory on the “/public” URL path:
addBundle(new AssetsBundle("/public/", 0, "/public"));
Now you can load the static assets in a web page:
<link rel='stylesheet' media='screen' href='/public/stylesheets/bootstrap.min.css'>
<script type='text/javascript' src='/public/javascripts/jquery.min.js'></script>Get the full source code for the Dropwizard WebJars demo on GitHub.
I’m sure there are other Java web frameworks that support WebJars, so if you know of one, let me know and I’ll try to create more demo projects.
Right now there are just a couple WebJars in the repository but if you’d like to see others then create a new issue on GitHub and I’ll build a new WebJar.
Let me know what you think about WebJars. Thanks!
About James Ward
James Ward (www.jamesward.com) works for Typesafe where he teaches developers the Typesafe Stack (Play Framework, Scala, and Akka) . James frequently presents at conferences around the world such as JavaOne, Devoxx, and many other Java get-togethers. Along with Bruce Eckel, James co-authored First Steps in Flex. He has also published numerous screencasts, blogs, and technical articles. Starting with Pascal and Assembly in the 80′s, James found his passion for writing code. Beginning in the 90′s he began doing web development with HTML, Perl/CGI, then Java. After building a Flex and Java based customer service portal in 2004 for Pillar Data Systems he became a Technical Evangelist for Flex at Adobe. In 2011 James became a Principal Developer Evangelist at Salesforce.com where he taught developers how to deploy apps on the cloud with Heroku. James Tweets as @_JamesWard and posts code at github.com/jamesward.
More About James »Northern Virginia Software Symposium
November 1 - 3, 2013
Reston, VA
Current Topics on the NFJS Tour
- Core Java, JEE
- Dynamic Languages: Groovy, JRuby, Scala, Clojure
- RESTful Web Apps
- Frameworks: Hibernate, Grails, Spring, JSF, GWT, more
- Agility
- Test Driven Design
- Security
- Ajax, Flex, RIA
Why Attend the NFJS Tour?
- » Cutting-Edge Technologies
- » Agile Practices
- » Peer Exchange
Current Topics:
- Languages on the JVM: Scala, Groovy, Clojure
- Enterprise Java
- Core Java, Java 7
- Agility
- Testing: Geb, Spock, Easyb
- REST
- NoSQL: MongoDB, Cassandra
- Hadoop
- Spring 3
- Automation Tools: Git, Hudson, Sonar
- HTML5, Ajax, jQuery, Usability
- Mobile Applications - iPhone and Android
- More...
NFJS, the Magazine
May Issue Now AvailableOn the road to learning
by Raju GandhiRefactoring to Modularity
by Kirk KnoernschildRESTful Groovy
by Kenneth KousenGetting Started with D3.js
by Brian Sletten