Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to use Namespace Typescript properly with Webpack

I am working on a new project with webpack. This is my first try with this tool.

I used to develop with typescript (for angularJS 1.5) since 1 year and I never had any problems relating to my namespacing.

// src/App/Core/Http/Test.ts
export namespace App.Core.Http {
      export class Test {
          public attr:any;
      }
 }

// src/App/Bootstrap.ts
import { App } from "./Core/Http/Test";
let testInstance = new App.Core.Http.Test();

What if I have more file to import. I can't import more than one "App" variable and I don't want to make alias each time I'm processing an import.

This is the case I don't want and I would like to fix :

// src/App/Bootstrap.ts
import { App } from "./Core/Http/Test";
import { App as App2 } from "./Core/Http/Test2"; // How can I import properly my namespace
let testInstance = new App.Core.Http.Test(),
    test2Instance = new App2.Core.Http.Test2();

Am I wrong with something or did I mess something about webpack ? How can I play with namespace like in PHP with webpack ?

EDIT 2016/22/07 at 6:26 PM

I learnt that it is not possible to use namespace using webpack. Why ? Because each .ts file are considered as a module with its own scope.

Module developement is required.

I've found a solution to get my file call clearer using module instead of namespace.

In my case, I have App/Core which contains Http, Service, Factory, Provider... folders. At the root of Core folder I created a index.ts file which export all my needed files with module architecture. Let's see.

// src/App/Core/index.ts
export module Http {
      export { Test } from "src/App/Core/Http/Test";
      export { Test2 } from "src/App/Core/Http/Test2";
      export { Test3 } from "src/App/Core/Http/Test3";
 }

export module Service {
      export { ServiceTest } from "src/App/Core/Service/ServiceTest";
      export { ServiceTest2 } from "src/App/Core/Service/ServiceTest2";
      export { ServiceTest3 } from "src/App/Core/Service/ServiceTest3";
}
//src/App/Core/index.ts ----> EOF 

And in another file call import the module with the alias Core.

// src/App/Bootstrap.ts
import { * as Core } from "./Core";

let TestInstance = new Core.Http.Test(),
    Test2Instance = new Core.Http.Test2(),
    TestInstance = new Core.Http.Test3();

let ServiceTestInstance = new Core.Service.Test(),
    ServiceTest2Instance = new Core.Service.Test2(),
    ServiceTestInstance = new Core.Service.Test3();

// src/App/Bootstrap.ts ----> EOF
like image 513
Disfigure Avatar asked Jul 22 '16 08:07

Disfigure


People also ask

Should I use namespace in TypeScript?

Don't use Custom TypeScript Modules and Namespaces Since we have ES6 modules as a standard in JavaScript, we don't need custom TypeScript modules and namespaces to organize our code. Instead, we should use standard JavaScript modules with import and export instead.

How do you call a namespace in TypeScript?

Namespace Declaration We can declare the namespace as below. To access the interfaces, classes, functions, and variables in another namespace, we can use the following syntax. If the namespace is in separate TypeScript file, then it must be referenced by using triple-slash (///) reference syntax.

How do namespaces work in TypeScript?

The namespace is used for logical grouping of functionalities. A namespace can include interfaces, classes, functions and variables to support a single or a group of related functionalities. A namespace can be created using the namespace keyword followed by the namespace name.

What is export namespace in TypeScript?

Namespaces are simply named JavaScript objects in the global scope. Namespaces are used for the grouping of variables, functions, objects, classes, and interfaces so that you can avoid the naming collisions. Namespaces are declared using the namespace keyword.


3 Answers

I learnt that it is not possible to use namespace using webpack. Why ? Because each .ts file are considered as a module with its own scope.

Module developement is required.

I've found a solution to get my file call clearer using module instead of namespace.

In my case, I have App/Core which contains Http, Service, Factory, Provider... folders. At the root of Core folder I created a index.ts file which export all my needed files with module architecture. Let's see.

// src/App/Core/index.ts
export module Http {
      export { Test } from "src/App/Core/Http/Test";
      export { Test2 } from "src/App/Core/Http/Test2";
      export { Test3 } from "src/App/Core/Http/Test3";
 }

export module Service {
      export { ServiceTest } from "src/App/Core/Service/ServiceTest";
      export { ServiceTest2 } from "src/App/Core/Service/ServiceTest2";
      export { ServiceTest3 } from "src/App/Core/Service/ServiceTest3";
}
//src/App/Core/index.ts ----> EOF 

And in another file call import the module with the alias Core.

// src/App/Bootstrap.ts
import { * as Core } from "./Core";

let TestInstance = new Core.Http.Test(),
    Test2Instance = new Core.Http.Test2(),
    TestInstance = new Core.Http.Test3();

let ServiceTestInstance = new Core.Service.Test(),
    ServiceTest2Instance = new Core.Service.Test2(),
    ServiceTestInstance = new Core.Service.Test3();

// src/App/Bootstrap.ts ----> EOF
like image 160
Disfigure Avatar answered Oct 03 '22 20:10

Disfigure


You should not be using namespaces and modules at the same time, even if you were not using webpack you would have the same problem

a normal approach with modules is to just export the class directly:

// src/App/Core/Http/Test.ts
export class Test {
    public attr:any;
}

// src/App/Bootstrap.ts
import { Test } from "./Core/Http/Test";
let testInstance = new Test();

the other example:

// src/App/Bootstrap.ts
import { Test} from "./Core/Http/Test";
import { Test2 } from "./Core/Http/Test2";
let testInstance = new Test(),
    test2Instance = new Test2();

hope this helps :)

like image 41
kruczy Avatar answered Oct 03 '22 21:10

kruczy


In TypeScript you can alias namespaces with another kind of import statement. It's pretty simple.

import { App } from "./Core/Http/Test";
import Test = App.Core.Http.Test;
import { App as App2 } from "./Core/Http/Test2";
import Test2 = App2.Core.Http.Test2;

At runtime, this is no different than const Test2 = App2.Core.Http.Test2; but at compile-time, using an import statement brings over all the type information, too.

like image 40
cspotcode Avatar answered Oct 03 '22 21:10

cspotcode