Search code examples
node.jsinversifyjs

InversifyJS - injectable is not a function


I'm trying to set up a NodeJS/TypeScript project using InversifyJS but I'm having some trouble getting off the ground. I've been looking at this for the past couple of days and can't figure out the issue. Everything builds correctly, but when I try to launch the Node server I get the following error:

TypeError: inversify_1.injectable is not a function

I'm running NodeJS v6.2.2 (Windows 10 x64) and have TypeScript 1.8 installed. I've tried building using both VS2015 and gulp. Below is a minimal example that I've tried that experiences the same error. I can't see anything wrong but I must be missing something obvious. (Sloppy code aside, it should still work.)

server.ts:

/// <reference path="./node_modules/reflect-metadata/reflect-metadata.d.ts" />
/// <reference path="./node_modules/inversify-dts/inversify/inversify.d.ts" />
/// <reference path="./typings/index.d.ts" />

import "reflect-metadata"
import { Application } from "./app/app"
import { ITest, TestClass } from "./app/testclass"
import { Kernel, injectable, inject } from "inversify"

var kernel = new Kernel();
kernel.bind<ITest>("ITest").to(TestClass);
kernel.bind<Application>(Application).to(Application);

var app = kernel.get<Application>(Application);
app.initialize();

app/app.ts

/// <reference path="../node_modules/inversify-dts/inversify/inversify.d.ts" />
/// <reference path="../typings/index.d.ts" />

import * as Hapi from "hapi";
import { inject, injectable } from "inversify"
import { ITest } from "../app/testclass"

@injectable()
export class Application {
    private testClass: ITest;

    constructor( @inject("ITest") test: ITest) {
        this.testClass = test;
    };

    initialize() {
        var server = new Hapi.Server({
            connections: {
                router: {
                    isCaseSensitive: false,
                    stripTrailingSlash: true
                }
            }
        });

        server.connection({
            port: '3000',
            host: 'localhost'
        });

        server.route({
            method: 'GET',
            path: '/',
            handler: (request: Hapi.Request, reply: Hapi.IReply) => {
                var str = this.testClass.test();
                reply(str);
            }
        });

        server.start(function () {
            console.log('Server running at:', server.info.uri);
        });
    }
}

app/testclass.ts

/// <reference path="../node_modules/inversify-dts/inversify/inversify.d.ts" />

import { injectable } from "inversify"

export interface ITest {
    test(): string;
}

@injectable()
export class TestClass implements ITest {
    test(): string {
        return "testing";
    }
}

tsconfig.json

{
    "files": [
        "server.ts",
        "app/app.ts",
        "app/testclass.ts"
    ],
    "compilerOptions": {
        "module": "commonjs",
        "noImplicitAny": true,
        "target": "es6",
        "experimentalDecorators": true,
        "emitDecoratorMetadata": true,
        "outDir": "../release/"
    }
}

full error output from node:

C:\Projects\inversifytest\release\app\app.js:50
    inversify_1.injectable(),
                ^

TypeError: inversify_1.injectable is not a function
    at Object.<anonymous> (C:\Projects\inversifytest\release\app\app.js:50:17)
    at Module._compile (module.js:541:32)
    at Object.Module._extensions..js (module.js:550:10)
    at Module.load (module.js:458:32)
    at tryModuleLoad (module.js:417:12)
    at Function.Module._load (module.js:409:3)
    at Module.require (module.js:468:17)
    at require (internal/module.js:20:19)
    at Object.<anonymous> (C:\Projects\inversifytest\release\server.js:6:15)
    at Module._compile (module.js:541:32)

Solution

  • I figured it out - it was a dumb mistake as I suspected. I had the wrong version of InversifyJS installed. The decorators only work with the new version 2.x and npm had installed 1.3.1 (because I didn't explicitly specify a version).