0

I'm using Visual Studio 2013 (Update 3), Node.js Tools v1.0.20721.02 and Node.js v0.10.31

I'm trying to put each class into its own file.
At design time everything seems fine, intellisense is working and the code compiles without issues.
At runtime however, node tells me it cannot find the classes.

I've reproduced this again and again by creating a new Node console project in Visual Studio

SomeClass.ts

export class SomeClass
{
    name: string;

    constructor(name: string)
    {
        this.name = name;
    }
}

app.ts

///<reference path="Scripts/typings/node/node.d.ts"/>

import some = require("SomeClass");

var instance = new some.SomeClass("Batman");
console.log(instance.name);

The generated javascript output looks like this:

SomeClass.js

var SomeClass = (function () {
    function SomeClass(name) {
        this.name = name;
    }
    return SomeClass;
})();
exports.SomeClass = SomeClass;
//# sourceMappingURL=SomeClass.js.map

app.js

///<reference path="Scripts/typings/node/node.d.ts"/>
var some = require("SomeClass");

var instance = new some.SomeClass("Batman");
console.log(instance.name);
//# sourceMappingURL=app.js.map

Runtime output

module.js:340
throw err;

Error: Cannot find module 'SomeClass'
at Function.Module._resolveFilename (module.js:338:15)
...

Visual Studio Solution structure

enter image description here

This is a standard solution created by the project template in Visual Studio, shouldn't it just work out of the box?

I've seen quite a few related questions, including this one, which seem to solve the
the issues most people are having, but don't seem to solve my problem.

Community
  • 1
  • 1
TimothyP
  • 21,178
  • 26
  • 94
  • 142

2 Answers2

1

Try using require("./SomeClass") instead:

node.js resolves require differently when there is no path prepended (see here), so in this case you need to tell it to look in the current directory, not for a core module or inside an (inexistent) node_modules directory.

Further info on why it does not fail before runtime, given by the OP in the comments:

Apparently VS resolves everything whether you prepend './' or not and at runtime node requires './' to be prepended.

yerforkferchips
  • 1,965
  • 1
  • 19
  • 27
0

Run your program again adding the following line before your require:

console.log("cwd:%s", process.cwd());

And adjust the path you require so it starts at your current working directory (cwd).

Rob Raisch
  • 17,040
  • 4
  • 48
  • 58
  • As in specify the full path in the require("f:\..\..\...") That doesn't seem to work nor does it make much sense. It should not be machine dependent. – TimothyP Sep 26 '14 at 14:06
  • Not the best solution, but it hints at the likely problem. Try using `require("./SomeClass")`. node.js resolves `require` differently when there is no path prepended ([see here](http://nodejs.org/api/modules.html#modules_loading_from_node_modules_folders)) – yerforkferchips Sep 26 '14 at 14:11
  • TimothyP, rather than being machine-dependent, Node resolves requires by attempting to find its target in the `node_modules` directory in the current working directory, then in `node_modules` in its parent directory, continuing up to the root directory. If you want to require modules outside of this strategy, you need to specify their paths either absolutely or relatively to the cwd. – Rob Raisch Sep 26 '14 at 14:32
  • I've added a screenshot of the solution explorer, because this stuff should just work out of the box. – TimothyP Sep 26 '14 at 14:52
  • @yerforkferchips You are correct, that solved the problem. Apparently VS resolves everything whether you prepend './' or not and at runtime node requires './' to be prepended. That solved the issue. If you put it as an answer I can even mark it as the solution – TimothyP Sep 26 '14 at 14:55