1 | /*
|
---|
2 | MIT License http://www.opensource.org/licenses/mit-license.php
|
---|
3 | Author Tobias Koppers @sokra
|
---|
4 | */
|
---|
5 |
|
---|
6 | "use strict";
|
---|
7 |
|
---|
8 | const asyncLib = require("neo-async");
|
---|
9 | const EntryDependency = require("./dependencies/EntryDependency");
|
---|
10 | const { someInIterable } = require("./util/IterableHelpers");
|
---|
11 | const { compareModulesById } = require("./util/comparators");
|
---|
12 | const { dirname, mkdirp } = require("./util/fs");
|
---|
13 |
|
---|
14 | /** @typedef {import("./Compiler")} Compiler */
|
---|
15 |
|
---|
16 | /**
|
---|
17 | * @typedef {Object} ManifestModuleData
|
---|
18 | * @property {string | number} id
|
---|
19 | * @property {Object} buildMeta
|
---|
20 | * @property {boolean | string[]} exports
|
---|
21 | */
|
---|
22 |
|
---|
23 | class LibManifestPlugin {
|
---|
24 | constructor(options) {
|
---|
25 | this.options = options;
|
---|
26 | }
|
---|
27 |
|
---|
28 | /**
|
---|
29 | * Apply the plugin
|
---|
30 | * @param {Compiler} compiler the compiler instance
|
---|
31 | * @returns {void}
|
---|
32 | */
|
---|
33 | apply(compiler) {
|
---|
34 | compiler.hooks.emit.tapAsync(
|
---|
35 | "LibManifestPlugin",
|
---|
36 | (compilation, callback) => {
|
---|
37 | const moduleGraph = compilation.moduleGraph;
|
---|
38 | asyncLib.forEach(
|
---|
39 | Array.from(compilation.chunks),
|
---|
40 | (chunk, callback) => {
|
---|
41 | if (!chunk.canBeInitial()) {
|
---|
42 | callback();
|
---|
43 | return;
|
---|
44 | }
|
---|
45 | const chunkGraph = compilation.chunkGraph;
|
---|
46 | const targetPath = compilation.getPath(this.options.path, {
|
---|
47 | chunk
|
---|
48 | });
|
---|
49 | const name =
|
---|
50 | this.options.name &&
|
---|
51 | compilation.getPath(this.options.name, {
|
---|
52 | chunk
|
---|
53 | });
|
---|
54 | const content = Object.create(null);
|
---|
55 | for (const module of chunkGraph.getOrderedChunkModulesIterable(
|
---|
56 | chunk,
|
---|
57 | compareModulesById(chunkGraph)
|
---|
58 | )) {
|
---|
59 | if (
|
---|
60 | this.options.entryOnly &&
|
---|
61 | !someInIterable(
|
---|
62 | moduleGraph.getIncomingConnections(module),
|
---|
63 | c => c.dependency instanceof EntryDependency
|
---|
64 | )
|
---|
65 | ) {
|
---|
66 | continue;
|
---|
67 | }
|
---|
68 | const ident = module.libIdent({
|
---|
69 | context: this.options.context || compiler.options.context,
|
---|
70 | associatedObjectForCache: compiler.root
|
---|
71 | });
|
---|
72 | if (ident) {
|
---|
73 | const exportsInfo = moduleGraph.getExportsInfo(module);
|
---|
74 | const providedExports = exportsInfo.getProvidedExports();
|
---|
75 | /** @type {ManifestModuleData} */
|
---|
76 | const data = {
|
---|
77 | id: chunkGraph.getModuleId(module),
|
---|
78 | buildMeta: module.buildMeta,
|
---|
79 | exports: Array.isArray(providedExports)
|
---|
80 | ? providedExports
|
---|
81 | : undefined
|
---|
82 | };
|
---|
83 | content[ident] = data;
|
---|
84 | }
|
---|
85 | }
|
---|
86 | const manifest = {
|
---|
87 | name,
|
---|
88 | type: this.options.type,
|
---|
89 | content
|
---|
90 | };
|
---|
91 | // Apply formatting to content if format flag is true;
|
---|
92 | const manifestContent = this.options.format
|
---|
93 | ? JSON.stringify(manifest, null, 2)
|
---|
94 | : JSON.stringify(manifest);
|
---|
95 | const buffer = Buffer.from(manifestContent, "utf8");
|
---|
96 | mkdirp(
|
---|
97 | compiler.intermediateFileSystem,
|
---|
98 | dirname(compiler.intermediateFileSystem, targetPath),
|
---|
99 | err => {
|
---|
100 | if (err) return callback(err);
|
---|
101 | compiler.intermediateFileSystem.writeFile(
|
---|
102 | targetPath,
|
---|
103 | buffer,
|
---|
104 | callback
|
---|
105 | );
|
---|
106 | }
|
---|
107 | );
|
---|
108 | },
|
---|
109 | callback
|
---|
110 | );
|
---|
111 | }
|
---|
112 | );
|
---|
113 | }
|
---|
114 | }
|
---|
115 | module.exports = LibManifestPlugin;
|
---|