Skip to content

sails.js fails if node_modules is not in same directory as the application #2505

Description

@kevinburke

The node.js application supports loading node_modules from a different folder via the NODE_PATH environment variable.

That way, I can put node_modules for my application in /usr/lib/node_modules (or wherever) and have my app in /opt/myapp and then run it with NODE_PATH=/usr/lib/node_modules node whateverscript.

Why would anyone want to do this? Well... we run Macs, but have an Ubuntu VM with Sails inside, so we can have a reproducible development environment, isolation, mirror what we run in production, etc. etc.

We have a shared folder in the VM which shares our application folder between the Mac and the VM. Running Sails with a node_modules directory in this shared folder was very very slow; on a brand new MacBook Pro, it was taking about 1 minute and 40 seconds to evaluate require('sails').load({verbose: true}). We don't have a crazy Sails application; maybe ~100 routes and ~50 models. (Running strace on our test runner showed that there were ~33,000 calls to stat; node is doing a lot of something to run the tests.) Anyway as you might imagine, hopping in and out of the VM this many times is slow and we were able to speed up require('sails').load from 100 seconds to 7 seconds by moving the node_modules directory inside the VM and loading it via the NODE_PATH variable mentioned above.

However, sails hard codes the node_modules path all over the place. Here's an example in upgrade-datastore.js:

      // Before trying to actually require the adapter, make sure we know the real module path:
      var node_modules = path.resolve(sails.config.appPath, 'node_modules');
      var modulePath = path.join(node_modules, moduleName);

      // Then make sure the module exists
      if (!fs.existsSync(modulePath)) {

        // If adapter doesn't exist, log an error and exit
        return Err.fatal.__UnknownAdapter__(connectionObject.adapter, modelID, sails.majorVersion, sails.minorVersion);
      }

This means that, despite node being able to run sails, load deps, etc from my external node_modules file, sails lays an egg when it can't find anything in the local node_modules.

We can get around this by symlinking node_modules back into the application folder, but it's pretty annoying. Would appreciate if the node_modules path was configurable, or at least respected the NODE_PATH environment variable.

I'm still sort of getting up to speed with node.js, but maybe require.resolve will do what you want? http://stackoverflow.com/a/15303236/329700

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions