Created by: natefaubion
This PR tweaks the way modules are handled. Previously we were just reading the -m
modules and concating the sources with the built in macros. I've added a new function expandModule
and tweaked the signature of expandTopLevel
. Both take a read tree as the first argument and an array of module contexts as the second. You can obtain module contexts by calling expandModule
. I've also added two exports to the main sweet
module: loadModule
and loadNodeModule
. loadModule
just takes a source string and returns a module context. loadNodeModule
will take a root
path and a node module name, read in the file, and call loadModule
. The node module will be looked up based on the root. So the sjs
binary uses process.cwd()
as the root, to look up modules from wherever it is invoked.
These serve as decent primitives for module loading. You could actually set up a tree of dependencies manually using this api. This also means that we can cache modules between calls to compile, which makes compiling multiple files really fast. The modules are only read in once instead of for every file. The test files all compile quicker, and the test suite (for me at least) has gone from nearly 4 seconds to 400 ms.
One thing I had to change was our usage of Map
from es6-collections
. Its implementation of Map
doesn't have any way to traverse keys, so it wasn't of much use to me for this. I have to be able to copy the env
of one module to another. I created a StringMap
constructor, which follows the same api, but uses a normal object as the store, and has an extend
method.
As an aside, is our usage of Map
necessary? I tried using StringMap
for everything, and all tests passed. I think template ids are just numbers, which works fine when coercing to a string for a key.