1

I'm trying to figure out if (and how, if it's possible) to use the RequireJS optimization tool to include not only my JavaScript modules, but also my "text!" modules. I'm working on a Durandal app that uses "text!" modules for views.

Sometimes we have users who get a timeout trying to load a view. Here's an example error:

Error: Load timeout for modules: text!views/primaryapplicants.html
http://requirejs.org/docs/errors.html#timeout

I've got another question I just posted about handling that timeout. I can't figure out how to intercept it and try again. I know the module definition is valid, it's just that customers may have a network connectivity issue--especially if they're on a cell phone.

However, as I've continued to ponder this, I realize that if I could simply package the entire app up into a single file, then we could avoid the extra HTTP calls--which might cut down on timeouts like this. It would mean the app either loads, or it doesn't--instead of the possibility of "partially" loading.

This app does not have a large number of views. I estimate that adding every view would add around 20kb with gzip compression.

So, is it possible to package these "text!" modules up somehow?

Community
  • 1
  • 1
Josh
  • 7,232
  • 8
  • 48
  • 75
  • 1
    Have you tried using Weyland http://durandaljs.com/documentation/Building-with-Weyland/ Durandal's builder? By default it will include all views as text!**/*.html. – RainerAtSpirit Oct 17 '13 at 21:50
  • I didn't even know it existed... so no, I haven't tried it. Will check that out. Thanks for the tip! – Josh Oct 21 '13 at 11:19
  • I don't have a weyland-config.js file, and there's no documentation on how to create one. It simply says '...details coming soon...'. So that's a non-started, unless I can find documentation on that somewhere else. Oh well, it seemed like the right solution. – Josh Oct 21 '13 at 12:32
  • Added a sample as answer. – RainerAtSpirit Oct 21 '13 at 12:41

2 Answers2

1

There is the inlineText build config option (true by default) which instructs the optimizer to do exactly what you want. One caveat is that it will, just like with any other module, only detect dependencies specified in some module's define() block. In other words, it won't be able to detect text! dependencies which are requested on demand, unless they're made reachable explicitly - and this is where your problem lies.

One workaround (far from ideal if you have many view files) would be to specify every single text! dependency you use in the include option inside your build config, e.g.:

// ...
include: ["text!views/primaryapplicants.html",
  "text!views/secondaryapplicants.html",
  // etc.
]
// ...
kryger
  • 12,906
  • 8
  • 44
  • 65
1

You might want to give weyland, Durandal's optimizer a try. An example weyland-config.js configuration can be found in the HTML StarterKit.

https://github.com/BlueSpire/Durandal/blob/master/platforms/HTML/StarterKit/weyland-config.js

exports.config = function(weyland) {
    weyland.build('main')
        .task.jshint({
            include:'app/**/*.js'
        })
        .task.uglifyjs({
            include:['app/**/*.js', 'lib/durandal/**/*.js']
        })
        .task.rjs({
            include:['app/**/*.{js,html}', 'lib/durandal/**/*.js'],
            loaderPluginExtensionMaps:{
                '.html':'text'
            },
            rjs:{
                name:'../lib/require/almond-custom', //to deploy with require.js, use the build's name here instead
                insertRequire:['main'], //not needed for require
                baseUrl : 'app',
                wrap:true, //not needed for require
                paths : {
                    'text': '../lib/require/text',
                    'durandal':'../lib/durandal/js',
                    'plugins' : '../lib/durandal/js/plugins',
                    'transitions' : '../lib/durandal/js/transitions',
                    'knockout': '../lib/knockout/knockout-2.3.0',
                    'bootstrap': '../lib/bootstrap/js/bootstrap',
                    'jquery': '../lib/jquery/jquery-1.9.1'
                },
                inlineText: true,
                optimize : 'none',
                pragmas: {
                    build: true
                },
                stubModules : ['text'],
                keepBuildDir: true,
                out:'app/main-built.js'
            }
        });
}
RainerAtSpirit
  • 3,723
  • 1
  • 17
  • 18
  • These paths are all different than what I've got in my app, but this is a great start. I'll be going through these one path at a time and adjust them for how my app is laid out. I thought for sure that I had started with a "starter kit" but apparently not as I'm missing the weyland-config.js file and my paths are a bit different. I'll report back how it goes. Thanks! – Josh Oct 21 '13 at 19:45
  • Well, this seemed promising, but after updating all the paths and trying to execute weyland, it fails with no error. No output at all, actually--even with the "-v" option (which is "use verbose logging"). That leaves me with no idea where to head next. I guess I'll try and get RequireJS's packaging working--and hope that the Durandal folks put together a little more documentation on Weyland! :-) – Josh Oct 21 '13 at 20:26