I used to have a simple filestructure of 5 files in one folder:
- classes.ts
- hello.ts
- types.ts
- functions.ts
- tsconfig.json
tsconfig.json:
{
"compilerOptions": {
"module": "commonjs",
"target": "es2015",
"sourceMap": false,
"strict": true,
"strictPropertyInitialization": false
},
"files": [
"classes.ts",
"hello.ts",
"functions.ts",
"types.ts"
],
"exclude": [
"node_modules"
]
}
However, as time passes I started to have type/interface/class names collision. The question is: how do I prevent classes.ts from knowing about a particular type (or all of them) from hello.ts? It seems like they were implicitly imported which isn't the desired behaviour for me.
I tried separating them into different folders with a different tsconfig.json per folder but then .ts files are not compiled all at once, just folder-by-folder.
CodePudding user response:
TypeScript distinguishes between two types of files:
- modules, which might be in CommonJS or ES dialects
- scripts, which do not use "import", "export", "module.exports", or any other module machinery, and consequently everything defined in a script goes into the global namespace.
As in the "Modules" Handbook docs, emphasis mine:
In TypeScript, just as in ECMAScript 2015, any file containing a top-level
import
orexport
is considered a module.Conversely, a file without any top-level import or export declarations is treated as a script whose contents are available in the global scope (and therefore to modules as well).
Despite your use of the term "import types", you clarified in the comments that these are scripts, such that these types are not imported as they would be in modules: Everything defined in the global namespaces is accessible to everything else defined in the global namespace. As in this Handbook reference example advocating for namespaces, emphasis mine:
As we add more validators, we’re going to want to have some kind of organization scheme so that we can keep track of our types and not worry about name collisions with other objects. Instead of putting lots of different names into the global namespace, let’s wrap up our objects into a namespace.
That Handbook reference page suggests one solution, which is to use the namespace
keyword to give potential collisions more specific names; you can then use aliases to reduce the length of the names to type. However, you might also consider using explicit modules, which were designed with modularity and name collision avoidance in mind.