6
6
7
7
import javascript
8
8
private import semmle.javascript.internal.CachedStages
9
+ private import semmle.javascript.internal.paths.PathExprResolver
9
10
10
11
/**
11
12
* A module, which may either be an ECMAScript 2015-style module,
@@ -68,7 +69,7 @@ abstract class Module extends TopLevel {
68
69
* This predicate is not part of the public API, it is only exposed to allow
69
70
* overriding by subclasses.
70
71
*/
71
- predicate searchRoot ( PathExpr path , Folder searchRoot , int priority ) {
72
+ deprecated predicate searchRoot ( PathExpr path , Folder searchRoot , int priority ) {
72
73
path .getEnclosingModule ( ) = this and
73
74
priority = 0 and
74
75
exists ( string v | v = path .getValue ( ) |
@@ -89,7 +90,7 @@ abstract class Module extends TopLevel {
89
90
* resolves to a folder containing a main module (such as `index.js`), then
90
91
* that file is the result.
91
92
*/
92
- File resolve ( PathExpr path ) {
93
+ deprecated File resolve ( PathExpr path ) {
93
94
path .getEnclosingModule ( ) = this and
94
95
(
95
96
// handle the case where the import path is complete
@@ -122,8 +123,14 @@ abstract class Import extends AstNode {
122
123
/** Gets the module in which this import appears. */
123
124
abstract Module getEnclosingModule ( ) ;
124
125
126
+ /** DEPRECATED. Use `getImportedPathExpr` instead. */
127
+ deprecated PathExpr getImportedPath ( ) { result = this .getImportedPathExpr ( ) }
128
+
125
129
/** Gets the (unresolved) path that this import refers to. */
126
- abstract PathExpr getImportedPath ( ) ;
130
+ abstract Expr getImportedPathExpr ( ) ;
131
+
132
+ /** Gets the imported path as a string. */
133
+ final string getImportedPathString ( ) { result = this .getImportedPathExpr ( ) .getStringValue ( ) }
127
134
128
135
/**
129
136
* Gets an externs module the path of this import resolves to.
@@ -132,45 +139,23 @@ abstract class Import extends AstNode {
132
139
* path is assumed to be a possible target of the import.
133
140
*/
134
141
Module resolveExternsImport ( ) {
135
- result .isExterns ( ) and result .getName ( ) = this .getImportedPath ( ) . getValue ( )
142
+ result .isExterns ( ) and result .getName ( ) = this .getImportedPathString ( )
136
143
}
137
144
138
145
/**
139
146
* Gets the module the path of this import resolves to.
140
147
*/
141
- Module resolveImportedPath ( ) {
142
- result .getFile ( ) = this .getEnclosingModule ( ) .resolve ( this .getImportedPath ( ) )
143
- }
144
-
145
- /**
146
- * Gets a module with a `@providesModule` JSDoc tag that matches
147
- * the imported path.
148
- */
149
- private Module resolveAsProvidedModule ( ) {
150
- exists ( JSDocTag tag |
151
- tag .getTitle ( ) = "providesModule" and
152
- tag .getParent ( ) .getComment ( ) .getTopLevel ( ) = result and
153
- tag .getDescription ( ) .trim ( ) = this .getImportedPath ( ) .getValue ( )
154
- )
155
- }
148
+ Module resolveImportedPath ( ) { result .getFile ( ) = this .getImportedFile ( ) }
156
149
157
150
/**
158
- * Gets a module in a `node_modules/@types/` folder that matches the imported module name .
151
+ * Gets the module the path of this import resolves to .
159
152
*/
160
- private Module resolveFromTypeRoot ( ) {
161
- result .getFile ( ) =
162
- min ( TypeRootFolder typeRoot |
163
- |
164
- typeRoot .getModuleFile ( this .getImportedPath ( ) .getValue ( ) )
165
- order by
166
- typeRoot .getSearchPriority ( this .getFile ( ) .getParentContainer ( ) )
167
- )
168
- }
153
+ File getImportedFile ( ) { result = ImportPathResolver:: resolveExpr ( this .getImportedPathExpr ( ) ) }
169
154
170
155
/**
171
- * Gets the imported module, as determined by the TypeScript compiler, if any .
156
+ * DEPRECATED. Use `getImportedModule()` instead .
172
157
*/
173
- private Module resolveFromTypeScriptSymbol ( ) {
158
+ deprecated Module resolveFromTypeScriptSymbol ( ) {
174
159
exists ( CanonicalName symbol |
175
160
ast_node_symbol ( this , symbol ) and
176
161
ast_node_symbol ( result , symbol )
@@ -190,42 +175,11 @@ abstract class Import extends AstNode {
190
175
Stages:: Imports:: ref ( ) and
191
176
if exists ( this .resolveExternsImport ( ) )
192
177
then result = this .resolveExternsImport ( )
193
- else (
194
- result = this .resolveAsProvidedModule ( ) or
195
- result = this .resolveImportedPath ( ) or
196
- result = this .resolveFromTypeRoot ( ) or
197
- result = this .resolveFromTypeScriptSymbol ( ) or
198
- result = resolveNeighbourPackage ( this .getImportedPath ( ) .getValue ( ) )
199
- )
178
+ else result = this .resolveImportedPath ( )
200
179
}
201
180
202
181
/**
203
182
* Gets the data flow node that the default import of this import is available at.
204
183
*/
205
184
abstract DataFlow:: Node getImportedModuleNode ( ) ;
206
185
}
207
-
208
- /**
209
- * Gets a module imported from another package in the same repository.
210
- *
211
- * No support for importing from folders inside the other package.
212
- */
213
- private Module resolveNeighbourPackage ( PathString importPath ) {
214
- exists ( PackageJson json | importPath = json .getPackageName ( ) and result = json .getMainModule ( ) )
215
- or
216
- exists ( string package |
217
- result .getFile ( ) .getParentContainer ( ) = getPackageFolder ( package ) and
218
- importPath = package + "/" + [ result .getFile ( ) .getBaseName ( ) , result .getFile ( ) .getStem ( ) ]
219
- )
220
- }
221
-
222
- /**
223
- * Gets the folder for a package that has name `package` according to a package.json file in the resulting folder.
224
- */
225
- pragma [ noinline]
226
- private Folder getPackageFolder ( string package ) {
227
- exists ( PackageJson json |
228
- json .getPackageName ( ) = package and
229
- result = json .getFile ( ) .getParentContainer ( )
230
- )
231
- }
0 commit comments