TypeScript-Handbook icon indicating copy to clipboard operation
TypeScript-Handbook copied to clipboard

typeRoots falls back to automatic inclusion of packages

Open expressiveco opened this issue 6 years ago • 10 comments

  • Currently, it is stated that

    If typeRoots is specified, only packages under typeRoots will be included.

    However, when types could not be found in the compilerOptions.typeRoots folders, compiler falls back to the automatic inclusion of @types packages.

  • Also, like compilerOptions.types, specifying compilerOptions.typeRoots:[] disables the automatic inclusion of @types packages

expressiveco avatar Jun 06 '18 13:06 expressiveco

However, when types could not be found in the compilerOptions.typeRoots folders, compiler falls back to the automatic inclusion of @types packages.

that is not accurate.. there are two parts of the process. there are global pacakges (e.g. node, jquery, etc..) and there are modules (e.g. react).

typeRoots controls the global side of things.. that means @types\node will be included even though you never have an import in your project like import ... from "node".

for modules, e.g. import .. from "react", module resolution will go through the normal process, and will try to find a module react. part of that is to fall back to node_modules\@types\react if non better was found.

mhegazy avatar Jun 06 '18 17:06 mhegazy

@mhegazy it is already about automatic inclusion of global packages, not about modules imported by import statements.

So, import statements fallback to node_modules\@types but also it fallback when types in typeRoots folders do not exist, even though it is not that significant.

expressiveco avatar Jun 07 '18 11:06 expressiveco

but also it fallback when types in typeRoots folders do not exist,

i do not think this is true.

mhegazy avatar Jun 07 '18 16:06 mhegazy

@mhegazy I tested it, will check again.

expressiveco avatar Jun 07 '18 16:06 expressiveco

c:\test\774>tree /f .
│   a.ts
│   package.json
│
└───node_modules
    └───@types
        └───node
                index.d.ts
                inspector.d.ts
                LICENSE
                package.json
                README.md


c:\test\774>tsc --v
Version 2.9.1

c:\test\774>tsc --listFiles a.ts
C:/Users/mhegazy/AppData/Roaming/npm/node_modules/typescript/lib/lib.d.ts                                               a.ts
c:/test/774/node_modules/@types/node/inspector.d.ts
c:/test/774/node_modules/@types/node/index.d.ts

c:\test\774>tsc --typeRoots ./a --listFiles a.ts
C:/Users/mhegazy/AppData/Roaming/npm/node_modules/typescript/lib/lib.d.ts
a.ts

mhegazy avatar Jun 07 '18 17:06 mhegazy

Try this;

tsc --typeRoots ./someEmptyFolder --listFiles a.ts

expressiveco avatar Jun 07 '18 18:06 expressiveco

c:\test\774>tree /f .
│   a.ts
│   package.json
│   tsconfig.json
│
├───emptyFolder
└───node_modules
    └───@types
        └───node
                index.d.ts
                inspector.d.ts
                LICENSE
                package.json
                README.md


c:\test\774>tsc --typeRoots ./emptyFolder --listFiles a.ts
C:/Users/mhegazy/AppData/Roaming/npm/node_modules/typescript/lib/lib.d.ts
a.ts

c:\test\774>tsc --listFiles a.ts
C:/Users/mhegazy/AppData/Roaming/npm/node_modules/typescript/lib/lib.d.ts
a.ts
c:/test/774/node_modules/@types/node/inspector.d.ts
c:/test/774/node_modules/@types/node/index.d.ts

mhegazy avatar Jun 07 '18 19:06 mhegazy

if i were to guess, you have an import somewhere in your file.

mhegazy avatar Jun 07 '18 19:06 mhegazy

You are right, it does not fallback with an empty typeRoots folder. So, i find out what i was doing. I have an empty sub-folder with my modules name under the typeRoots folder so, it causes the module folder resolved by fallback to the node_modules/@types.

tree /f .
D:/TestProject
│   tsconfig.json
│
├───node_modules
│   └───@types
│       └───mymodule
│               index.d.ts
│
├───someFolder
│   └───mymodule
└───wwwroot
    └───js
            site.ts
  • node_modules/@​types/mymodule/index.d.ts
declare module 'mymodule' {
  export = myClass;
}
declare const myClass: myClass_;
interface myClass_ {
}

  • wwwroot/js/site.ts
var  a  =  myClass;
tsc --listFiles --traceResolution --typeRoots someFolder ./wwwroot/js/site.ts
======== Resolving type reference directive 'mymodule', containing file 'D:/TestProject/__inferred type names__.ts', root directory 'someFolder'. ========
Resolving with primary search path 'someFolder'.
File 'someFolder/mymodule/package.json' does not exist.
File 'someFolder/mymodule/index.d.ts' does not exist.
Looking up in 'node_modules' folder, initial location 'D:/TestProject'.
File 'D:/TestProject/node_modules/mymodule.d.ts' does not exist.
File 'D:/TestProject/node_modules/@types/mymodule/package.json' does not exist.
File 'D:/TestProject/node_modules/@types/mymodule.d.ts' does not exist.
File 'D:/TestProject/node_modules/@types/mymodule/index.d.ts' exist - use it as a name resolution result.
Resolving real path for 'D:/TestProject/node_modules/@types/mymodule/index.d.ts', result 'D:/TestProject/node_modules/@types/mymodule/index.d.ts'.
======== Type reference directive 'mymodule' was successfully resolved to 'D:/TestProject/node_modules/@types/mymodule/index.d.ts', primary: false. ========
C:/Users/exp/AppData/Roaming/npm/node_modules/typescript/lib/lib.d.ts
wwwroot/js/site.ts
D:/TestProject/node_modules/@types/mymodule/index.d.ts

expressiveco avatar Jun 08 '18 11:06 expressiveco

Yes. the assumption here is that every subfolder in your typesRoot is a declaration package and not a random folder.

mhegazy avatar Jun 08 '18 16:06 mhegazy