Closed johntron closed 9 years ago
Hmm, I think I'd prefer to just export require. So instead of only allowing you to require one file (cursor-move
) I think you should be able to require anything. In your example, it would probably change to:
<script src="build/index.js"></script>
<script>
var Cursor = require('root/index.js');
var Emitter = require('emitter');
...
</script>
Open to ideas though, cc/ @duojs/owners
Exporting require
is a really good idea imo, especially if we ever want to support bundling.
If we're concerned about clashing in the global namespace, perhaps we could create a duo
namespace, and add a var require = duo.noConflict()
(ala jQuery
-> $
) in cases where require
is in some sort of flux.
i'd much rather export require
than duo
@stephenmathieson We'd export both, just like jQuery exports both $
and jQuery
. But duo.noConflict()
would exist just in case something else decides to overwrite require
.
-1 from me. component did just fine only exposing require
.
if a specific env already exposes require
, why not do something like this:
build.js:
echo ";(function(){" > $@
duo < index.js >> $@
echo "window.duo = require;" >> $@
echo "})();" >> $@
Yeah, multiple libraries clobbering require
is probably not nearly as common/likely as the multiple JS libraries fighting over the $
var.
Yeah, exposing require
would be great - any idea how? Internally, it doesn't seem to maintain a list of names for each module:
require('component/model') Uncaught Error: cannot find module "component/model"
window.require.modules Object {1: Array[2], 2: Array[2], 3: Array[2], 4: Array[2], ... }
window.require.cache Object {1: Object, 2: Object, 3: Object, 4: Object, ... }
You have to know the numeric ID to use:
require(2) function createModel(name) { ... }
There's this part in require.js:
// expose as `name`.
if (name) cache[name] = cache[id];
... but with my testing, name
is never set.
... but with my testing, name is never set.
name is only set for standalone modules: https://github.com/duojs/duo/blob/master/lib/duo.js#L465-L469
I'm not exactly sure how we'd support this feature at the moment, but ideally it would be as flexible as node's. I'm not sure we have this flexibility using pre-compiling, so at the very least, I think it should be able to require
any top-level entry module. an additional nice-to-have would be requiring any component. That's trickier though, because the install and build step are merged.
I think we'd need to modify duo-pack
to support this feature, with potentially a few modification here: https://github.com/duojs/duo/blob/master/lib/duo.js#L461-L474
I've been working on a better implementation. Currently, I have window.require() working (see see johntron/pack@a2b5909), but the paths aren't intuitive – they have to match the include paths of the packed code. This means, for example, if my compiled code contains require('component/model')
, I have to type exactly that in the browser. I cannot for instance type require('component/model:index.js')
from Chrome's console. It also means some really strange paths are possible (i.e. require('./2.js:component/model:index.js')
), but I'm not too concerned with this, since this is more for debugging purposes.
The way this currently works is by generating a lookup (require.lookup
) to map component names to the numeric IDs used in the packed code. To get require() working in the browser for paths that weren't explicitly used in the compiled code, I was thinking of generating a big long list of all the possible paths; however, I seem to remember Component doing this, and my compiled code was massive as a result.
Instead, I'd like to resolve paths inside require() if it's feasible. Duo has already done the heavy-lifting of downloading dependencies and putting them in the right spot, so I'd need to write a couple of methods to look up files using relative paths and component paths. I found this changeset for Component that might help.
Just like to point out that you can encounter require()
conflicting in the namespace with Atom-Shell. As it can provide node require()
js calls on the frontend, which has caused some problems loading in js libs via script tags that have module detection and completely break unless loaded via require()
.
Node's doesn't appear to support cdn urls so I'm looking for an alternative, being able to require via an alternative namespace could be handy. Either that or I'm too new to module loaders, majority seem to require a build step, it doesn't seem that I can load a script via url in the client and assign it to a var var momentjs = require( 'url/to/moment.min.js' )
. Being able to use duo()
or duo.require()
would be nice.
If we decide to expose require
globally, I think we'll approach it a little differently. Since this has been open for so long, I'm just going to close it.
Adds --with_require to make example HTML easier. See https://github.com/duojs/duo/issues/350
For example, you could run:
Then use this in example.html: