LinkedInAttic / inject

AMD and CJS dependency management in the browser
http://www.injectjs.com
Other
464 stars 48 forks source link

No caching? and addRule questions... #140

Closed jfrux closed 12 years ago

jfrux commented 12 years ago

I'm trying to understand this, I really am!

So I have a few basic things I'd like to be in my apps by default...

jQuery, jQuery UI, Twitter Bootstrap, Underscore, and Backbone.

So here it is, this is my issue. I've isolated the code to this folder so it would be as clean as possible: Checkout this link to see the problem. http://ccpd.uc.edu/static/injectjs/

It's pulling in the files but it's never calling the "console.log" that occurs within my bootloader.js module.

It's also not caching.

If I remove the addRules for Underscore / Backbone it will get to the console.log but it won't cache the files ever... Not sure what's going on :-\

Just trying to understand if this library is going to work for us or not :)

jfrux commented 12 years ago

Here is a link to the gist: https://gist.github.com/3228262

jfrux commented 12 years ago

UPDATE: Okay, I figured out that underscore was being required automatically by Backbone inside the code. So now my console.log is working...

However, I don't quite understand the whole "exports" stuff... Is this even going to work right for me?

Should I be able to write Backbone / jQuery, etc. freely inside my modules as long as I put them as dependencies?

Can I augment modules somehow? Same module / scope but different js files? I'm trying to wrap my mind around all of this and I think I'm getting stuck in module pattern mindset too much haha.

jakobo commented 12 years ago

Sorry for the delays, been a bit busy at LinkedIn.

I see that bootloader.js is creating a Backbone collection and then assigning it to its exports. You'll just need to use those exports after they've been required.

app.js is both set up to configure and run things. I'd make the following changes

1) rename the call to "bootloader" inside of app.js to an initializer

// old
require.run("bootloader");
// ---
// new
require.run("initialize");

2) create a new file initialize.js which is where we'll kick off the Backbone framework

// this is initialize.js
var Bootloader = require("bootloader");
console.log(Bootloader);
  // console.log will show the object assigned to module.exports
  // it will contain a property "Collection" which was the backbone collection object

The purpose of the exports is to store the objects for access later. The require.run() call just executes one time, without actually doing any callbacks. The new file we made, initialize.js will ensure the bootloader object is available, and will let you then operate on the backbone collection created inside of bootloader.js

Hope this helps! A robust example can be found at a tutorial for require.js - http://backbonetutorials.com/organizing-backbone-using-modules/ Inject is AMD compliant, so the same code ideas should apply (and inject supports define() as well)

jakobo commented 12 years ago

Also, I pulled up your example and it seems to be caching bootloader.js in localstorage like it should. If you're not seeing the caching take place, can you provide browser information? It may actually be an (unrelated) bug. Cheers!

jfrux commented 12 years ago

I'm going to give this another round of implementing it. I think I'm starting to understand it's true potential... I spent a couple of weeks with a few different alternatives and I keep coming back to this one.

Thanks for all your hard work.

jfrux commented 12 years ago

Okay, am I being dumb...?

I've added three rules

Inject.addRule(/^jquery$/, {
      path: "../vendor/jquery/jquery",
      pointcuts: {
        after: function() {
          module.setExports(jQuery.noConflict());
          delete window["jQuery"];
        }
      }
    });

    Inject.addRule(/^underscore$/, {
      path: "../vendor/underscore/underscore",
      pointcuts: {
        after: function() {
          module.setExports(_.noConflict());
          delete window["_"];
        }
      }
    });

    Inject.addRule(/^backbone$/, {
      path: "../vendor/backbone/backbone",
      pointcuts: {
        after: function() {
            module.setExports(Backbone.noConflict());
            delete window["Backbone"];
        }
      }
    });

But "exports" in the dom is only containing "_" instead of all of them...? I don't think I quite understand what I'm doing! :P :)

jakobo commented 12 years ago

That looks right. What does the code look like that is using backbone, underscore, and jquery?