I like keeping myself busy building modular web-applications, but don't want to spend time where I can save some..
For example I'm building a news module that should be easily implemented over multiple sites, because the same web-application is used.
However not all websites will need a news module. Is it better/easier/faster to create an inline stylesheet/javascript file built into the module itself, than to create a big external stylesheet/javascript with all the libraries? Even though the file for the news module is not needed on all other webpages?
It seems to be much easier to create an inline library in the module itself. So that this only gets loaded when needed, and saves load time and bandwidth on the other pages.
The other thing is that I like writing 'plug-and-play' modules. Say I move a file across the file server into the module folder, and the application will take care of the rest. With inline sheets, I dont have to add new lines to the header/footer etc.
What is the best solution for this? When also taking into account that I rather spend 10 minutes moving a file and it works, than to spend 1 hour appending external libraries just because its more of a 'good practice'?
If you re building web applications, are you using the MVC patern? Do you separate your concerns? (your Templates/Views, your Models, and your logic(Controllers))
If you follow MVC, it makes easier maintaining and customizing your app.
To answer to your exact question, what you need is RequireJS. This way you have only one place to declare your requirements, and RequireJS will handle the rest.. Load order and more..
Quoting from the requirejs website:
Over time, if you start to create more modular code that needs to be
reused in a few places, the module format for RequireJS makes it easy
to write encapsulated code that can be loaded on the fly.
Inline is never a solid way to maintain CSS. Take care to separate the description of your layout from your views. You can easily include the file in the same directory as the module so it should not be an issue.
Or if you want just to load "on fly" some script you can use jQuery.getScript , http://api.jquery.com/jQuery.getScript/ . Otherwise you should follow George's way.
Related
I'm working on a web project that uses webgl content generated with unity. When trying to load the required js files the browser freezes for around 30 seconds. The main js file has 35MB size unzipped so this seems to be the cause.
I want to avoid this freeze if possible but I couldn't manage to do it using WebWorkers since the script needs access to UI. My other possible solution is to try to split the js file into smaller ones but I don't know how to do it. Do you have any suggestions?
If you add async to your script tag like this <script async src="app.min.js"></script> it will not block rendering anymore. Also caching the script in the browser or delivering it from a CDN can help reduce the download time.
35MB are, however, way too much for a website. Are you sure there isn't a lot of unused stuff like libraries in it?
We recently wrote an article with web performance best practices, with explanations to critical rendering path and other fronted concerns here
35 MB just for the JS file seems ridiculous. It could be that the entire build is probably of that size (textures, media, etc.). Have a look here on how to reduce the build size.
Though 35 MB is wayyyy to much for a JS file, you can start by following pointers:
Create utilities and reuse the code. This can be at any level. Be it generic component (HTML generating code) or validation logic, if it can be configured using arguments, make a function and use it.
If you have Hard-coded JSON in your js, move them to .josn files and load them only when they are required.
Split files based on sections in view. In SPAs, there are cases when a section is not visible. For such cases, don't load such files. Spread your code base from 1 file to 100s of file.
If you have a lot of event listeners, move them to different file. You can have section_event.js, section_data.json, section_utils.js and section_index.js. If there involves lot of data parsing, you can even have section_parser.js
Basic Idea is to split code into multiple files. Then, make code more reusable. You can even look into loading libraries to reduce your load.
Also, load a resource only when required. SPA have stages. Load concerned files when they are needed. Split download from 1 time to partial, on-demand approach. Also look into webpack or grunt or gulp to minify js.
So my question is mainly about the use case of RequireJS.
I read a lot about pure javascript driven web pages. Currently I extend single rendered views (e.g. provided by a PHP Framework) with AngularJS which adds a lot of value.
Sadly the dependency management gets harder and harder with every <script> tag on other 'single pages'. Even more when there is a main.js file which provides common libraries (e.g. jQuery and AngularJS itself).
I thought this doesn't fit into RequireJS philosophy to have one main file which requires all dependencies.
A good example would be an administration panel which uses some modules (defined by AngularJS's dependencies).
Example:
scripts/
adminpanel/
panel.app.js
panel.filters.js
panel.directives.js
antoherModule/
andAntoherModule/
require.js
tl;dr
When you use AngularJS to extend single pages, instead of building a completely javascript driven web application, is it good practice to use RequireJS for AMD loading modules which will be used on the single page ? And how is the best way to do it so ?
SPA usually means that the page doesn't refresh and all extra content is loaded on the fly. In essence the entire app is a single page. It doesn't mean that all of the content is loaded on the initial load (though if it is small enough, this could be the case). Using RequireJS / AMD architecture is really good for this kind of thing.
As the user navigates throughout the site, different partials / templates are retrieved as well as any supporting JavaScript.
The best way to do this is with define. Defining all of the requirements your script needs in order to work. All of the scripts needed will be loaded before the function is run, ensuring that you have everything you need. Furthermore, the items that you define as requirements can have their own define to specify the scripts they need... and so on.
We are developing a javascript component to be used in a JSF app and we're using Dojo.
The thing is we only need specific parts of the library and we'd like to only insert into our webapp the files/folders we use to accomplish our goal.
We could do this 'by hand' but in the future we might need to add other functionality from Dojo and then we will not know what resources we need -> I guess by this moment you realised we are no Dojo/js gurus.
Basically we are looking for a way to automate this process. We were thinking of getting a list of the dependencies and then create a small script to 'filter' the files.
Is this possible ? Have anyone tried this before ?
Thanks.
I may be misinterpreting your request, but I think dojo does what you want out of the box. Since the latest versions of dojo follow the Asynchronous Module Definition (AMD) format, you use a global require function to describe what dependencies a specific block of code have, and only those modules are loaded. An example from the sitepen dojo intro:
require(["dojo/dom", "dojo/domReady!"], function(dom){
var greeting = dom.byId("greeting");
greeting.innerHTML += " from Dojo!";
});
If you only want to have to to load a single <script/> tag, you'll want to look into the dojo builder. Using the online build tool You can select what packages you want included into the dojo.js layer and it will bundle everything up into a zip file that includes dojo.js/dojo.js.uncompressed.js which contains dojo core in addition to the modules you selected.
Ok, we did this by doing the following (just in case anyone will need this):
* declare a JSF filter and map it to /js/* (all dojo resources are under /js folder, this may need to be modified to fit your folder structure); this way, all requests for a dojo resource will be filtered.
* in the filter class, get all the requested files: (HttpServletRequest) request).getRequestURI() and write it line by line in a file: now you have all the needed resources.
* parse that file with a script, line by line, and copy the files to another location -> build the folder structure.
* use the created files in your WebContent folder (or wherever you need it), you have a clean library -> you only deploy what you use.
The web is littered with full-blown JavaScript libraries who say they will save your day and make your web development life much easier. You get encouraged to include these “mere 80 kb” libraries that is supposed to be the solution to all your needs, and practically make the web site work by itself. Needless to say, I’m not a big follower of JavaScript libraries,, especially since they almost always include lots of superfluous code, so I thought I’d put together a tiny library with only essential JavaScript functions.
The result of that is EJ – Essential JavaScript.
EJ consists of functions that I use all the time and they make writing JavaScript go faster and the result is being able to do work more efficiently. It is also about having the things you would write again and again for every web site you produce in one neat and tiny file instead, to be able to focus on the new things you need to address
This may be a dumb question for web guys. But I am a little confused over this. Now, I have an application where I am using a couple of Javascript files to perform different tasks. Now, I am using Javascript bundler to combine and minify all the files. So, at runtime there will be only one app.min.js file. Now, Requirejs is used to load modules or files at runtime. So, the question is if I already have all things in one file, then do I need requirejs? Or what is a use case scenario where I can use requirejs and/or bundler?
Please let me know if any further details are needed.
Generally you only use RequireJS in its loading form during development. Once the site is done and ready for deployment, you minify the code. The advantage here is RequireJS knows exactly what your dependencies are, and thus can easily minify the code in the correct order. Here is what it says on the RequireJS website:
Once you are finished doing development and want to deploy your code for your end users, you can use the optimizer to combine the JavaScript files together and minify it. In the example above, it can combine main.js and helper/util.js into one file and minify the result.
This is a hotly contested issue among many proficient javascript developers. Many other languages have a "compilation" phase where the entire program is bundled up for deployment (JBoss's .WAR files come to mind). Programmers that come from more traditional backgrounds often favor this approach.
Javascript has seen such growth in recent years that it is difficult to chart exact best practices, but those that appreciate the more functional nature of Javascript often prefer the module loading approach (like require.js uses).
I wrote Frame.js which works much like require.js, so my bias is towards the module loader approach.
To answer your question directly, yes, it is one or the other.
Most that argue for packing your scripts into a single file believe it enables more compression and is thus more efficient. I believe the efficiency advantages of packaging are negligible in most cases because: (1) module load times are distributed over the entire session, (2) individual modules can be compressed to nearly the same percentage, (3) individual modules can be cached by the server and routers separately, and (4) loading scripts only when they are needed ultimately allows you load less code for some users and more code overall.
In the long run, if you can see an advantage to dynamic script loading use it. If not, bundle your scripts into a single file.
It depends on your application. If you're making a server-side app with only modest javascript (less than 100kb minified) then go for total bundling, you're probably going to be fine.
But if you're making a javascript app and have a ton of code in it, then your needs are going to be different.
For example, in my app I bundle all the core files. There's jQuery, underscore, backbone, my main app files, my user login system, my layout system, my notifications and chat system, all are part of my big initial file.
But I have many other modules as well that isn't part of the initial bundle, that are loaded after those.
The forums, the wiki, the wysiwyg, color picker, drag/drop, calendar, and some animation files are part of the second category. You need to make reasonable decisions about what's commonly used and needed immediately vs what can be delayed.
If I include everything immediately I can get above a meg of javascript, which would be insane and make the initial boot unacceptably slow.
The second category starts downloading after initSuccess event fires from the initial file.
But the second category is more intelligent than the first in that it loads what's more important first. For example if you're looking at the wiki it'll load the wiki before it loads the color picker.
some time ago, I was reading an article(a library built by some guy) about how his library can do
lazy loading of JS
resolve dependencies between JS
(typically encountered when trying
to "include" one js from another)
include files only once. thought
specified multiple times regardless
of how they are called (either
directly specifying it as file or
specifying it as one of the
dependencies)
I forgot to bookmark it, what a mistake. Can some one point me to something which can do the above. I know DOJO and YUI library have something like this, but I am looking for something which I can use with jQuery
I am probably looking for one more feature as well.
My site has asp.net user controls
(reusable server side code snippets)
which have some JS. Some of them get
fired right away, when the page is
loading which gives a bad user
experience. Yahoo performance
guidelines specify that JS should
be at the bottom of the page, but
this is not possible in my case as
this would require me to separate the
JS and the corresponding server side
control into different files and
maintenance would be difficult. I
definitely can put a jQuery
document.ready() in my user control
JS to make sure that it fires only
after the DOM has loaded, but I am
looking for a simpler solution.
Is there anyway that I could say "begin executing any JS only after DOM has loaded" in a global way than just writing "document.ready" within every user control ?
Microsoft Research proposed a new tool called DOLOTO. It can take care of rewriting & function splitting and enable the on-demand js loading possible.
From the site..
Doloto is a system that analyzes
application workloads and
automatically performs code splitting
of existing large Web 2.0
applications. After being processed by
Doloto, an application will initially
transfer only the portion of code
necessary for application
initialization. The rest of the
application's code is replaced by
short stubs -- their actual function
code is transferred lazily in the
background or, at the latest,
on-demand on first execution.
OK I guess I found the link
[>10 years ago; now they are all broken]
http://ajaxian.com/archives/usingjs-manage-javascript-dependencies
http://www.jondavis.net/techblog/post/2008/04/Javascript-Introducing-Using-%28js%29.aspx
I also found one more, for folks who are interested in lazy loading/dynamic js dependency resolution
http://jsload.net/
About the lazy-loading scripts thingy, most libraries just adds a <script> element inside the HTML pointing to the JS file to be "included" (assynchronously), while others like DOJO, fetches it's dependencies using a XMLHttpRequest and then eval's its contents, making it work synchronously.
I've used the YUI-Loader that is pretty much simple to use and you don't need the whole library to get it working. There are other libraries that gives you just this specific funcionality, but I think YUI's is the safe choice.
About your last question, I don't think there's something like that. You would have to do it yourself, but it would be similar to using document.ready.
i did in my framework a similar thing:
i created a include_js(file); that include the js file only if it isn't included reading and executing it with a synchronous ajax call.
Simply put that code in top of the page that needs dependencies and you're done!