I have a question regarding JavaScript bundling methodology.
We have any existing Java Web application (A product) consisting of lot of jsps. We wanted to implement the bundling and minification methodology for the js and CSS files in order reduce the overhead(). As I mentioned this is a Product it comes with its traditional web folder structure
Is there any way (Any tool) through which we can have a dynamic bundling methodology without changing the syntax in jsp. If we change the syntax in jsps then this will increase our overhead during upgrade activities.
Jawr is a tunable packaging solution for Javascript and CSS which allows for rapid development of resources in separate module files. Developers can work with a large set of split javascript files in development mode, then Jawr bundles all together into one or several files in a configurable way.
By using a tag library, Jawr allows you to use the same, unchanged pages for development and production. Jawr also minifies and compresses the files, resulting in reduced page load times.
Jawr is configured using a simple .properties descriptor, and aside of standard java web applications it can also be used with Facelets, Grails, Wicket and Spring applications.
https://jawr.java.net
Related
I have two JavaScript single-page applications in two separate GIT repositories. I want to keep them separated as much as possible (different teams working on them etc.), but they are still very closely related and even co-exist within the context of the same web page as part of one large SPA. Naturally, these two applications share large amounts of library code and it is very wasteful to bundle each with its own copy of libraries.
Is there any way I can reuse the library code? What would be a possible approach?
What I am describing seems to be achievable using the DLL plugin. Basically, I create a vendor.js file, which requires all of the dependencies. Then, from that file generate a bundle of all the libraries and a manifest.json file. Then, using DllReferencePlugin it should be possible to tell webpack in each of my apps to take the dependency from the vendor bundle. Both apps can be built independently. As a last step, simply load of the three bundles on the page.
How to create a build system for number of JS client applications, all using same framework but different combinations of framework parts? This would enable all client applications receive the framework updates automatically, without having to rely on one distribution file, containing all framework abilities (which would be rather sub-optimal).
In best case scenario, the client applications would use the only specific parts (raw, non-minimized files) from the framework project, while when deployed, the application would have only one script containing only the needed functionalities of the framework. Also, if(/when) all this can't be done automatically, there should be only one "makefile" that would be used for both, loading single files in development and building the single JS file for deployment.
GWT does what you are requesting through a feature called deferred binding.
http://code.google.com/webtoolkit/doc/latest/DevGuideCodingBasicsDeferred.html
THE GWT compiler generates many versions of code at compile time,
versions are created automatically per browser type, and it's possible to extend this functionality to other parameters such as user localization preferences or completely arbitrary parameters.
I finally managed to do this with combination of custom buildfiles, custom runtime build system done in PHP, sophisticated JavaScript non-coupling framework and massive Ant build scripts, doing the compiling and deployment. :P
Is there any software package/library that will produce a consolidated, minified JavaScript file for a production environment, while leaving the original files/references as-is in a development environment (so developers can work independently)?
JAWR does this (and more) for a Java/Groovy environment, but I haven't seen anything like it for the Microsoft .NET/IIS7 stack. Any pointers would be helpful. Thanks!
If you're looking for a good way to automatically compress and combine css & js files here are some options:
Xpedite Not bad: has one big disadantage: you can't combine files (js/css) that are included in usercontrols with the files in your page.
Shinkansen, I don't have a lot of experience with it, but I know it has a lot of configuration options.
The ClientDependency Framework was originally written for Umbraco. Now there is a package available via NuGet for both WebForms and MVC. It works really well and this is my favorite.
We use YUICompressor to minify our Javascript (and CSS) and it works well.
However, we've had to write our own HttpHandler to decide whether to minify or not on the fly, depending on a config setting (but it could equally be on whether it was a DEBUG or RELEASE build).
In fact, we cache the file once minified (or not), so we don't have to do the same process on every request.
I'm currently developing an application that will be run on local network in B2B environment. So I can almost forget about micro(mini?) optimizations in terms of saving bandwidth because Hardware Is Cheap, Programmers Are Expensive.
We have a well structured Object oriented js code in the project and obviously lots of js classes. If all the classes will be stored in separated files then it will be quite easy to navigate through this code and hence maintain it.
But this will bring my browser to generate a couple dozens of HTTP requests to get all the js files/classes I need on the page. Even in local environment it is not super fast on first load(with empty cache), and later when you modify it and cache has to be invalidated.
Possible solutions:
violate rule "one class per file"
use YUI compressor all the time(in development & production) for generating one big js file.
But if we choose YUI compressor for this(no minify action in dev environment, and minify for production) - then we need to reload/recompile this big js file on every modification in any js file.
What would you recommend for solving this problem?
Keep all the .js files separate. Keep your "one class per file" rule.
Then, use a server-side technology to aggregate the script into one request.
Options:
Use an ASPX or PHP or whatevver server-side scripting thing you have, to aggregate all the JS into one request. The request for a .js is no longer a static file, but with caching on the server it should be relatively cheap to serve.
Use Server Side Includes in a consolidated .js file.
<!--#include virtual="/class1.js"-->
<!--#include virtual="/class2.js"-->
Your approach of having separate files for each class is good - practices that make development easier are always good.
Here's some tips for making the loading faster:
Compress your code. As you say, you could use YUICompressor, or the newly released Google Closure Compiler.
When concatenating multiple files into one, think of what you need and when: If you only need files A, B and C when the app starts, but not Z and X, put only A, B and C into a single file. Load another file with Z and X concurrently after A/B/C.
You can use Firefox plugins YSlow and Page Speed to test for load performance bottlenecks
As you mention, you would need to rerun the compressor each time you make a change. I don't think this is a big problem - on a decent machine, it should run pretty fast even with a lot of files. Alternatively, you could use a daily build process using some tool, which could build the latest revision from your source control (you do use scm, right?), and run unit tests and deploy if everything goes OK.
I would recommend using Ant or some other automation tool to create a build script. This will make it as simple as running one command to build your compressed script, reducing the repetitive work you would otherwise need to do. You could even have Ant deploy your code to the server.
You may have the best of both worlds - a development environment with one class per js file without the need to compile/deploy for every iteration AND one (or several) concatenated larger js files (minified if desired) in production.
Depending on your build environment this may be setup in a number of different ways, but using Ant may be the easiest way. Using Ant you can run tasks for both concatenation and minification (running YUICompressor through the Java task). This will produce the concatenated and minified large js file.
However, to maintain productivity you want to avoid doing this for every code iteration. Changing the tags from one to several (for every class file) is out of the question.
So, you load your big js file as expected:
<script src="application.js"></script>
When deploying to production this file is the concatenated/minified version of all your js files.
However, during development this file is a bootstrap/loader file that simply loads all your individual js-files (illustrative example using jQuery).
$.getScript('/class1.js');
$.getScript('/class2.js');
$.getScript('/class3.js');
$.getScript('/class4.js');
$.getScript('/classn.js');
....
If you are using YUI 3 look into the module behavior and how to specify dependencies.
Using different Ant targets the generation and copying of these files to the correct location may easily be managed.
And now you may simply reload your browser whenever you need to test a change in a file, but get the performance benefit during production. All without sacrificing productivity or maintainability.
On a recent project I have been working on in C#/ASP.NET I have some fairly complicated JavaScript files and some nifty Style Sheets. As these script resources grow in size it is advisable to minify the resources and keep your web pages as light as possible, of course. I know many developers who hand-feed their JavaScript resources into compressors after debugging and then deploy their applications.
When it comes to source control and automated builds in the satisfying world of continuous integration (thank you CruiseControl.NET); hand compression will simply not do. The only way to maintain source control and offer compressed resources is to keep JS/CSS source & their minified brethren in a separate directory structure. Then register only one set of resources or the other in code-behind. However, if a developer makes a change to JS/CSS source and then fails to re-compact it and check in both versions, then you’re code-line is now out of sync. Not to mention inelegant.
I am thinking that it would be nice to write a custom executable (if one does not exist yet) for the CC.NET task block which would find and compress all JavaScript and CSS resources in the target directory after the build action but before the asp.net publish to target. This way, developers would only work on JS and CSS source and users would only get the minified resources.
Is there an application that already performs this task and if not, what kind of resource(s) should I look to install on the build server to have CC.NET execute?
(The closest question I could find here to this one required NAnt, which is not an option in my case.)
EDIT:
Dave Ward now has a great article on how to automatically minify in Visual Studio at his site.
The MSBuildCommunityTasks Project has a few MSBuild tasks that may do what you are looking for including Merge and JSCompress.
You could add these into your MSBuild project in the AfterBuild target to allow the project to perform this action every time the project is built and nothing would ever be out of sync. Your web application could then reference the compacted version for run but the developers would edit the full versions.
Nothing else would be needed on the server except the MSBuild community tasks assembly. You can put this assembly in your own source tree and reference from there and your CI build should get that assembly and everything it needs when it builds.
Another JS (and CSS!) compression library for MSBuild:
http://www.codeplex.com/YUICompressor
This is a .NET port of the java-based Yahoo! compressor.
Not a perfect answer, but if you're using MVC4 they've built this in as a new feature. When running a Debug configuration, it outputs individual files with comments and such but when you switch to Release, it will automatically bundle, minify, and change in page references to the minified files. You can setup separate bundles for, say, jquery and your own js. This works with CSS and JS files.
http://www.asp.net/mvc/tutorials/mvc-4/bundling-and-minification
If MVC4 doesn't work for you, you can also find packages on Nuget that can help such as this:
https://www.nuget.org/packages?q=minify