source: imaps-frontend/node_modules/webpack/lib/dependencies/CommonJsExportRequireDependency.js@ 79a0317

main
Last change on this file since 79a0317 was 79a0317, checked in by stefan toskovski <stefantoska84@…>, 3 days ago

F4 Finalna Verzija

  • Property mode set to 100644
File size: 11.5 KB
Line 
1/*
2 MIT License http://www.opensource.org/licenses/mit-license.php
3 Author Tobias Koppers @sokra
4*/
5
6"use strict";
7
8const Dependency = require("../Dependency");
9const { UsageState } = require("../ExportsInfo");
10const Template = require("../Template");
11const { equals } = require("../util/ArrayHelpers");
12const makeSerializable = require("../util/makeSerializable");
13const propertyAccess = require("../util/propertyAccess");
14const { handleDependencyBase } = require("./CommonJsDependencyHelpers");
15const ModuleDependency = require("./ModuleDependency");
16const processExportInfo = require("./processExportInfo");
17
18/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */
19/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */
20/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */
21/** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */
22/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */
23/** @typedef {import("../ExportsInfo")} ExportsInfo */
24/** @typedef {import("../ExportsInfo").ExportInfo} ExportInfo */
25/** @typedef {import("../Module")} Module */
26/** @typedef {import("../ModuleGraph")} ModuleGraph */
27/** @typedef {import("../javascript/JavascriptParser").Range} Range */
28/** @typedef {import("../serialization/ObjectMiddleware").ObjectDeserializerContext} ObjectDeserializerContext */
29/** @typedef {import("../serialization/ObjectMiddleware").ObjectSerializerContext} ObjectSerializerContext */
30/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */
31/** @typedef {import("./CommonJsDependencyHelpers").CommonJSDependencyBaseKeywords} CommonJSDependencyBaseKeywords */
32
33const idsSymbol = Symbol("CommonJsExportRequireDependency.ids");
34
35const EMPTY_OBJECT = {};
36
37class CommonJsExportRequireDependency extends ModuleDependency {
38 /**
39 * @param {Range} range range
40 * @param {Range | null} valueRange value range
41 * @param {CommonJSDependencyBaseKeywords} base base
42 * @param {string[]} names names
43 * @param {string} request request
44 * @param {string[]} ids ids
45 * @param {boolean} resultUsed true, when the result is used
46 */
47 constructor(range, valueRange, base, names, request, ids, resultUsed) {
48 super(request);
49 this.range = range;
50 this.valueRange = valueRange;
51 this.base = base;
52 this.names = names;
53 this.ids = ids;
54 this.resultUsed = resultUsed;
55 this.asiSafe = undefined;
56 }
57
58 get type() {
59 return "cjs export require";
60 }
61
62 /**
63 * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module
64 */
65 couldAffectReferencingModule() {
66 return Dependency.TRANSITIVE;
67 }
68
69 /**
70 * @param {ModuleGraph} moduleGraph the module graph
71 * @returns {string[]} the imported id
72 */
73 getIds(moduleGraph) {
74 return (
75 /** @type {TODO} */ (moduleGraph.getMeta(this))[idsSymbol] || this.ids
76 );
77 }
78
79 /**
80 * @param {ModuleGraph} moduleGraph the module graph
81 * @param {string[]} ids the imported ids
82 * @returns {void}
83 */
84 setIds(moduleGraph, ids) {
85 /** @type {TODO} */ (moduleGraph.getMeta(this))[idsSymbol] = ids;
86 }
87
88 /**
89 * Returns list of exports referenced by this dependency
90 * @param {ModuleGraph} moduleGraph module graph
91 * @param {RuntimeSpec} runtime the runtime for which the module is analysed
92 * @returns {(string[] | ReferencedExport)[]} referenced exports
93 */
94 getReferencedExports(moduleGraph, runtime) {
95 const ids = this.getIds(moduleGraph);
96 const getFullResult = () => {
97 if (ids.length === 0) {
98 return Dependency.EXPORTS_OBJECT_REFERENCED;
99 }
100 return [
101 {
102 name: ids,
103 canMangle: false
104 }
105 ];
106 };
107 if (this.resultUsed) return getFullResult();
108 /** @type {ExportsInfo | undefined} */
109 let exportsInfo = moduleGraph.getExportsInfo(
110 /** @type {Module} */ (moduleGraph.getParentModule(this))
111 );
112 for (const name of this.names) {
113 const exportInfo = /** @type {ExportInfo} */ (
114 exportsInfo.getReadOnlyExportInfo(name)
115 );
116 const used = exportInfo.getUsed(runtime);
117 if (used === UsageState.Unused) return Dependency.NO_EXPORTS_REFERENCED;
118 if (used !== UsageState.OnlyPropertiesUsed) return getFullResult();
119 exportsInfo = exportInfo.exportsInfo;
120 if (!exportsInfo) return getFullResult();
121 }
122 if (exportsInfo.otherExportsInfo.getUsed(runtime) !== UsageState.Unused) {
123 return getFullResult();
124 }
125 /** @type {string[][]} */
126 const referencedExports = [];
127 for (const exportInfo of exportsInfo.orderedExports) {
128 processExportInfo(
129 runtime,
130 referencedExports,
131 ids.concat(exportInfo.name),
132 exportInfo,
133 false
134 );
135 }
136 return referencedExports.map(name => ({
137 name,
138 canMangle: false
139 }));
140 }
141
142 /**
143 * Returns the exported names
144 * @param {ModuleGraph} moduleGraph module graph
145 * @returns {ExportsSpec | undefined} export names
146 */
147 getExports(moduleGraph) {
148 if (this.names.length === 1) {
149 const ids = this.getIds(moduleGraph);
150 const name = this.names[0];
151 const from = moduleGraph.getConnection(this);
152 if (!from) return;
153 return {
154 exports: [
155 {
156 name,
157 from,
158 export: ids.length === 0 ? null : ids,
159 // we can't mangle names that are in an empty object
160 // because one could access the prototype property
161 // when export isn't set yet
162 canMangle: !(name in EMPTY_OBJECT) && false
163 }
164 ],
165 dependencies: [from.module]
166 };
167 } else if (this.names.length > 0) {
168 const name = this.names[0];
169 return {
170 exports: [
171 {
172 name,
173 // we can't mangle names that are in an empty object
174 // because one could access the prototype property
175 // when export isn't set yet
176 canMangle: !(name in EMPTY_OBJECT) && false
177 }
178 ],
179 dependencies: undefined
180 };
181 }
182 const from = moduleGraph.getConnection(this);
183 if (!from) return;
184 const reexportInfo = this.getStarReexports(
185 moduleGraph,
186 undefined,
187 from.module
188 );
189 const ids = this.getIds(moduleGraph);
190 if (reexportInfo) {
191 return {
192 exports: Array.from(
193 /** @type {TODO} */ (reexportInfo).exports,
194 name => ({
195 name,
196 from,
197 export: ids.concat(name),
198 canMangle: !(name in EMPTY_OBJECT) && false
199 })
200 ),
201 // TODO handle deep reexports
202 dependencies: [from.module]
203 };
204 }
205 return {
206 exports: true,
207 from: ids.length === 0 ? from : undefined,
208 canMangle: false,
209 dependencies: [from.module]
210 };
211 }
212
213 /**
214 * @param {ModuleGraph} moduleGraph the module graph
215 * @param {RuntimeSpec} runtime the runtime
216 * @param {Module} importedModule the imported module (optional)
217 * @returns {{exports?: Set<string>, checked?: Set<string>} | undefined} information
218 */
219 getStarReexports(
220 moduleGraph,
221 runtime,
222 importedModule = /** @type {Module} */ (moduleGraph.getModule(this))
223 ) {
224 /** @type {ExportsInfo | undefined} */
225 let importedExportsInfo = moduleGraph.getExportsInfo(importedModule);
226 const ids = this.getIds(moduleGraph);
227 if (ids.length > 0)
228 importedExportsInfo = importedExportsInfo.getNestedExportsInfo(ids);
229 /** @type {ExportsInfo | undefined} */
230 let exportsInfo = moduleGraph.getExportsInfo(
231 /** @type {Module} */ (moduleGraph.getParentModule(this))
232 );
233 if (this.names.length > 0)
234 exportsInfo = exportsInfo.getNestedExportsInfo(this.names);
235
236 const noExtraExports =
237 importedExportsInfo &&
238 importedExportsInfo.otherExportsInfo.provided === false;
239 const noExtraImports =
240 exportsInfo &&
241 exportsInfo.otherExportsInfo.getUsed(runtime) === UsageState.Unused;
242
243 if (!noExtraExports && !noExtraImports) {
244 return;
245 }
246
247 const isNamespaceImport =
248 importedModule.getExportsType(moduleGraph, false) === "namespace";
249
250 /** @type {Set<string>} */
251 const exports = new Set();
252 /** @type {Set<string>} */
253 const checked = new Set();
254
255 if (noExtraImports) {
256 for (const exportInfo of /** @type {ExportsInfo} */ (exportsInfo)
257 .orderedExports) {
258 const name = exportInfo.name;
259 if (exportInfo.getUsed(runtime) === UsageState.Unused) continue;
260 if (name === "__esModule" && isNamespaceImport) {
261 exports.add(name);
262 } else if (importedExportsInfo) {
263 const importedExportInfo =
264 importedExportsInfo.getReadOnlyExportInfo(name);
265 if (importedExportInfo.provided === false) continue;
266 exports.add(name);
267 if (importedExportInfo.provided === true) continue;
268 checked.add(name);
269 } else {
270 exports.add(name);
271 checked.add(name);
272 }
273 }
274 } else if (noExtraExports) {
275 for (const importedExportInfo of /** @type {ExportsInfo} */ (
276 importedExportsInfo
277 ).orderedExports) {
278 const name = importedExportInfo.name;
279 if (importedExportInfo.provided === false) continue;
280 if (exportsInfo) {
281 const exportInfo = exportsInfo.getReadOnlyExportInfo(name);
282 if (exportInfo.getUsed(runtime) === UsageState.Unused) continue;
283 }
284 exports.add(name);
285 if (importedExportInfo.provided === true) continue;
286 checked.add(name);
287 }
288 if (isNamespaceImport) {
289 exports.add("__esModule");
290 checked.delete("__esModule");
291 }
292 }
293
294 return { exports, checked };
295 }
296
297 /**
298 * @param {ObjectSerializerContext} context context
299 */
300 serialize(context) {
301 const { write } = context;
302 write(this.asiSafe);
303 write(this.range);
304 write(this.valueRange);
305 write(this.base);
306 write(this.names);
307 write(this.ids);
308 write(this.resultUsed);
309 super.serialize(context);
310 }
311
312 /**
313 * @param {ObjectDeserializerContext} context context
314 */
315 deserialize(context) {
316 const { read } = context;
317 this.asiSafe = read();
318 this.range = read();
319 this.valueRange = read();
320 this.base = read();
321 this.names = read();
322 this.ids = read();
323 this.resultUsed = read();
324 super.deserialize(context);
325 }
326}
327
328makeSerializable(
329 CommonJsExportRequireDependency,
330 "webpack/lib/dependencies/CommonJsExportRequireDependency"
331);
332
333CommonJsExportRequireDependency.Template = class CommonJsExportRequireDependencyTemplate extends (
334 ModuleDependency.Template
335) {
336 /**
337 * @param {Dependency} dependency the dependency for which the template should be applied
338 * @param {ReplaceSource} source the current replace source which can be modified
339 * @param {DependencyTemplateContext} templateContext the context object
340 * @returns {void}
341 */
342 apply(
343 dependency,
344 source,
345 {
346 module,
347 runtimeTemplate,
348 chunkGraph,
349 moduleGraph,
350 runtimeRequirements,
351 runtime
352 }
353 ) {
354 const dep = /** @type {CommonJsExportRequireDependency} */ (dependency);
355 const used = moduleGraph
356 .getExportsInfo(module)
357 .getUsedName(dep.names, runtime);
358
359 const [type, base] = handleDependencyBase(
360 dep.base,
361 module,
362 runtimeRequirements
363 );
364
365 const importedModule = moduleGraph.getModule(dep);
366 let requireExpr = runtimeTemplate.moduleExports({
367 module: importedModule,
368 chunkGraph,
369 request: dep.request,
370 weak: dep.weak,
371 runtimeRequirements
372 });
373 if (importedModule) {
374 const ids = dep.getIds(moduleGraph);
375 const usedImported = moduleGraph
376 .getExportsInfo(importedModule)
377 .getUsedName(ids, runtime);
378 if (usedImported) {
379 const comment = equals(usedImported, ids)
380 ? ""
381 : `${Template.toNormalComment(propertyAccess(ids))} `;
382 requireExpr += `${comment}${propertyAccess(usedImported)}`;
383 }
384 }
385
386 switch (type) {
387 case "expression":
388 source.replace(
389 dep.range[0],
390 dep.range[1] - 1,
391 used
392 ? `${base}${propertyAccess(used)} = ${requireExpr}`
393 : `/* unused reexport */ ${requireExpr}`
394 );
395 return;
396 case "Object.defineProperty":
397 throw new Error("TODO");
398 default:
399 throw new Error("Unexpected type");
400 }
401 }
402};
403
404module.exports = CommonJsExportRequireDependency;
Note: See TracBrowser for help on using the repository browser.