Make extra/* compatible with TypeScript / ES 6
authorTim Düsterhus <duesterhus@woltlab.com>
Mon, 8 Feb 2021 14:44:26 +0000 (15:44 +0100)
committerTim Düsterhus <duesterhus@woltlab.com>
Mon, 8 Feb 2021 14:44:26 +0000 (15:44 +0100)
extra/_buildCore.js
extra/_buildExternal.js
extra/compiler.js
extra/package-lock.json
extra/package.json

index 3486c2686f16d14fa14a92e024938b1f6f7dfed2..4abc243da3670ef39c43bc481c4890faf3d7a389 100644 (file)
@@ -2,120 +2,118 @@ const childProcess = require("child_process");
 const compiler = require("./compiler");
 const fs = require("fs");
 
-function compile(destination, files, overrides) {
-       let minifiedData = [];
-
-       files.forEach((filename) => {
-               minifiedData.push({
-                       filename: filename,
-                       content: compiler.compile(fs.readFileSync(process.cwd() + `/${filename}`, "utf-8"), overrides),
-               });
-       });
-
+async function compile(destination, files, overrides) {
        let content = `// ${destination} -- DO NOT EDIT\n\n`;
 
-       minifiedData.forEach((fileData) => {
-               content += `// ${fileData.filename}\n`;
-               content += `(function (window, undefined) { ${fileData.content.code} })(this);`;
+       for (const filename of files) {
+               const output = await compiler.compile(fs.readFileSync(process.cwd() + `/${filename}`, "utf-8"), overrides);
+
+               content += `// ${filename}\n`;
+               content += `(function (window, undefined) { ${output.code} })(this);`;
                content += "\n\n";
-       });
+       };
 
        fs.writeFileSync(destination, content);
 }
 
-//
-// step 1) build `WCF.Combined.min.js` and `WCF.Combined.tiny.min.js`
-//
-process.chdir("../wcfsetup/install/files/js/");
-[true, false].forEach((COMPILER_TARGET_DEFAULT) => {
-       let output = "WCF.Combined" + (COMPILER_TARGET_DEFAULT ? "" : ".tiny") + ".min.js";
-       console.time(output);
-       {
-               let data = fs.readFileSync(".buildOrder", "utf8");
-               let files = data
-                       .trim()
-                       .split(/\r?\n/)
-                       .map((filename) => `${filename}.js`);
-
-               compile(output, files, {
-                       compress: {
-                               global_defs: {
-                                       COMPILER_TARGET_DEFAULT: COMPILER_TARGET_DEFAULT,
+(async () => {
+       //
+       // step 1) build `WCF.Combined.min.js` and `WCF.Combined.tiny.min.js`
+       //
+       process.chdir("../wcfsetup/install/files/js/");
+       for (const COMPILER_TARGET_DEFAULT of [true, false]) {
+               let output = "WCF.Combined" + (COMPILER_TARGET_DEFAULT ? "" : ".tiny") + ".min.js";
+               console.time(output);
+               {
+                       let data = fs.readFileSync(".buildOrder", "utf8");
+                       let files = data
+                               .trim()
+                               .split(/\r?\n/)
+                               .map((filename) => `${filename}.js`);
+
+                       await compile(output, files, {
+                               compress: {
+                                       global_defs: {
+                                               COMPILER_TARGET_DEFAULT: COMPILER_TARGET_DEFAULT,
+                                       },
                                },
-                       },
-               });
-       }
-       console.timeEnd(output);
-});
-
-//
-// step 2) Redactor II + plugins
-//
-const redactorCombined = "redactor.combined.min.js";
-process.chdir("3rdParty/redactor2/");
-
-console.time(redactorCombined);
-{
-       let files = ["redactor.js"];
-       fs.readdirSync("./plugins/").forEach((file) => {
-               file = `plugins/${file}`;
-               let stat = fs.statSync(file);
-               if (stat.isFile() && !stat.isSymbolicLink()) {
-                       files.push(file);
+                       });
                }
-       });
+               console.timeEnd(output);
+       }
 
-       compile(redactorCombined, files);
-}
-console.timeEnd(redactorCombined);
-
-//
-// step3) build rjs
-//
-const rjsCmd = process.platform === "win32" ? "r.js.cmd" : "r.js";
-process.chdir("../../");
-
-{
-       let configFile = "require.build.js";
-       let outFilename = require(process.cwd() + `/${configFile}`).out;
-
-       [true, false].forEach((COMPILER_TARGET_DEFAULT) => {
-               let overrides =
-                       "uglify2.compress.global_defs.COMPILER_TARGET_DEFAULT=" +
-                       (COMPILER_TARGET_DEFAULT ? "true" : "false");
-               if (!COMPILER_TARGET_DEFAULT) {
-                       outFilename = outFilename.replace(/\.min\.js$/, ".tiny.min.js");
-                       overrides += " out=" + outFilename;
-               }
+       //
+       // step 2) Redactor II + plugins
+       //
+       const redactorCombined = "redactor.combined.min.js";
+       process.chdir("3rdParty/redactor2/");
 
-               console.time(outFilename);
-               childProcess.execSync(`${rjsCmd} -o ${configFile} ${overrides}`, {
-                       cwd: process.cwd(),
-                       stdio: [0, 1, 2],
+       console.time(redactorCombined);
+       {
+               let files = ["redactor.js"];
+               fs.readdirSync("./plugins/").forEach((file) => {
+                       file = `plugins/${file}`;
+                       let stat = fs.statSync(file);
+                       if (stat.isFile() && !stat.isSymbolicLink()) {
+                               files.push(file);
+                       }
                });
-               console.timeEnd(outFilename);
-       });
-}
 
-//
-// step 4) legacy ACP scripts
-//
-process.chdir("../acp/js/");
+               await compile(redactorCombined, files);
+       }
+       console.timeEnd(redactorCombined);
 
-fs.readdirSync("./")
-       .filter((filename) => {
-               let stat = fs.statSync(filename);
-               if (stat.isFile() && !stat.isSymbolicLink()) {
-                       return filename.match(/\.js$/) && !filename.match(/\.min\.js$/);
-               }
+       //
+       // step3) build rjs
+       //
+       const rjsCmd = process.platform === "win32" ? "r.js.cmd" : "r.js";
+       process.chdir("../../");
 
-               return false;
-       })
-       .forEach((filename) => {
-               console.time(filename);
-               {
-                       let output = compiler.compile(fs.readFileSync(process.cwd() + `/${filename}`, "utf-8"));
-                       fs.writeFileSync(filename.replace(/\.js$/, ".min.js"), output.code);
+       {
+               let configFile = "require.build.js";
+               let outFilename = require(process.cwd() + `/${configFile}`).out;
+
+               for (const COMPILER_TARGET_DEFAULT of [true, false]) {
+                       let overrides = "";
+                       if (!COMPILER_TARGET_DEFAULT) {
+                               outFilename = outFilename.replace(/\.min\.js$/, ".tiny.min.js");
+                               overrides += " out=" + outFilename;
+                       }
+
+                       console.time(outFilename);
+                       {
+                               childProcess.execSync(`${rjsCmd} -o ${configFile} ${overrides}`, {
+                                       cwd: process.cwd(),
+                                       stdio: [0, 1, 2],
+                               });
+                               const output = await compiler.compile(fs.readFileSync(outFilename, "utf-8"));
+                               fs.writeFileSync(outFilename, output.code);
+                       }
+                       console.timeEnd(outFilename);
                }
-               console.timeEnd(filename);
-       });
+       }
+
+       //
+       // step 4) legacy ACP scripts
+       //
+       process.chdir("../acp/js/");
+
+       await Promise.all(fs.readdirSync("./")
+               .filter((filename) => {
+                       const stat = fs.statSync(filename);
+                       if (stat.isFile() && !stat.isSymbolicLink()) {
+                               return filename.match(/\.js$/) && !filename.match(/\.min\.js$/);
+                       }
+
+                       return false;
+               })
+               .map(async (filename) => {
+                       console.time(filename);
+                       {
+                               const output = await compiler.compile(fs.readFileSync(process.cwd() + `/${filename}`, "utf-8"));
+                               fs.writeFileSync(filename.replace(/\.js$/, ".min.js"), output.code);
+                       }
+                       console.timeEnd(filename);
+               }));
+
+})();
index c62a97e52539aa8672c334491cd54ff69b7f849a..ae41687478e824b416aea7e55f0d87ed5c8c2f91 100644 (file)
@@ -39,12 +39,12 @@ fs.readdirSync("./")
 
                     return false;
                 })
-                .forEach(filename => {
-                    [true, false].forEach(COMPILER_TARGET_DEFAULT => {
+                .forEach(async filename => {
+                    for (const COMPILER_TARGET_DEFAULT of [true, false]) {
                         let outFilename = filename.replace(/\.js$/, (COMPILER_TARGET_DEFAULT ? "" : ".tiny") + ".min.js");
                         console.time(outFilename);
                         {
-                            let output = compiler.compile(fs.readFileSync(path + filename, 'utf-8'), {
+                            let output = await compiler.compile(fs.readFileSync(path + filename, 'utf-8'), {
                                 compress: {
                                     global_defs: {
                                         COMPILER_TARGET_DEFAULT: COMPILER_TARGET_DEFAULT
@@ -55,18 +55,18 @@ fs.readdirSync("./")
                             fs.writeFileSync(path + outFilename, output.code);
                         }
                         console.timeEnd(outFilename);
-                    });
+                    };
                 });
         }
     });
 
 const rjsCmd = (process.platform === "win32") ? "r.js.cmd" : "r.js";
-rjsPaths.forEach(path => {
+rjsPaths.forEach(async path => {
     let buildConfig = `${path}require.build.js`;
     let outFilename = require(process.cwd() + `/${buildConfig}`).out;
 
-    [true, false].forEach(COMPILER_TARGET_DEFAULT => {
-        let overrides = "uglify2.compress.global_defs.COMPILER_TARGET_DEFAULT=" + (COMPILER_TARGET_DEFAULT ? "true" : "false");
+    for (const COMPILER_TARGET_DEFAULT of [true, false]) {
+        let overrides = "";
         if (!COMPILER_TARGET_DEFAULT) {
             outFilename = outFilename.replace(/\.min\.js$/, '.tiny.min.js');
             overrides += " out=" + outFilename;
@@ -77,6 +77,8 @@ rjsPaths.forEach(path => {
             cwd: path,
             stdio: [0, 1, 2]
         });
+        const output = await compiler.compile(fs.readFileSync(path + '/' + outFilename, "utf-8"));
+        fs.writeFileSync(path + '/' + outFilename, output.code);
         console.timeEnd(outFilename);
-    });
+    };
 });
index f5f18eb6ce7a2d407fae78c4b8a65d7823e16238..704178e05ff4c3d30b85acd867c9870c17caf151 100644 (file)
@@ -1,7 +1,8 @@
 const fs = require("fs");
-const uglify = require("uglify-js");
+const terser = require("terser");
+const merge = require('deepmerge')
 
-const uglifyJsConfig = {
+const terserConfig = {
     compress: {
         sequences: true,
         properties: true,
@@ -18,15 +19,20 @@ const uglifyJsConfig = {
         global_defs: {
             COMPILER_TARGET_DEFAULT: false
         }
+    },
+    format: {
+        comments: false,
     }
 };
 
 module.exports = {
     compile: (filename, overrides) => {
         if (overrides === undefined) overrides = {};
+        const config = merge(terserConfig, overrides);
 
-        return uglify.minify(
+        return terser.minify(
             filename,
-            Object.assign(uglifyJsConfig, overrides));
+            config
+        );
     }
 }
index f571786fa98f42bd9d6a64c50b6ecb67ebd71232..eecdfde933c93d907bfd85345d7d9ef6480eb779 100644 (file)
@@ -1,6 +1,178 @@
 {
+  "name": "pwd",
+  "lockfileVersion": 2,
   "requires": true,
-  "lockfileVersion": 1,
+  "packages": {
+    "": {
+      "dependencies": {
+        "deepmerge": "^4.2.2",
+        "requirejs": "^2.3.6",
+        "terser": "^5.6.0-beta",
+        "ts-node": "^8.10.2"
+      },
+      "devDependencies": {
+        "@types/md5-file": "^4.0.2",
+        "@types/node": "^14.6.0",
+        "md5-file": "^5.0.0",
+        "typescript": "^4.0.2"
+      }
+    },
+    "node_modules/@types/md5-file": {
+      "version": "4.0.2",
+      "resolved": "https://registry.npmjs.org/@types/md5-file/-/md5-file-4.0.2.tgz",
+      "integrity": "sha512-8gacRfEqLrmZ6KofpFfxyjsm/LYepeWUWUJGaf5A9W9J5B2/dRZMdkDqFDL6YDa9IweH12IO76jO7mpsK2B3wg==",
+      "dev": true
+    },
+    "node_modules/@types/node": {
+      "version": "14.6.0",
+      "resolved": "https://registry.npmjs.org/@types/node/-/node-14.6.0.tgz",
+      "integrity": "sha512-mikldZQitV94akrc4sCcSjtJfsTKt4p+e/s0AGscVA6XArQ9kFclP+ZiYUMnq987rc6QlYxXv/EivqlfSLxpKA==",
+      "dev": true
+    },
+    "node_modules/arg": {
+      "version": "4.1.3",
+      "resolved": "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz",
+      "integrity": "sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA=="
+    },
+    "node_modules/buffer-from": {
+      "version": "1.1.1",
+      "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz",
+      "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A=="
+    },
+    "node_modules/commander": {
+      "version": "2.20.3",
+      "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz",
+      "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ=="
+    },
+    "node_modules/deepmerge": {
+      "version": "4.2.2",
+      "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.2.2.tgz",
+      "integrity": "sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==",
+      "engines": {
+        "node": ">=0.10.0"
+      }
+    },
+    "node_modules/diff": {
+      "version": "4.0.2",
+      "resolved": "https://registry.npmjs.org/diff/-/diff-4.0.2.tgz",
+      "integrity": "sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==",
+      "engines": {
+        "node": ">=0.3.1"
+      }
+    },
+    "node_modules/make-error": {
+      "version": "1.3.6",
+      "resolved": "https://registry.npmjs.org/make-error/-/make-error-1.3.6.tgz",
+      "integrity": "sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw=="
+    },
+    "node_modules/md5-file": {
+      "version": "5.0.0",
+      "resolved": "https://registry.npmjs.org/md5-file/-/md5-file-5.0.0.tgz",
+      "integrity": "sha512-xbEFXCYVWrSx/gEKS1VPlg84h/4L20znVIulKw6kMfmBUAZNAnF00eczz9ICMl+/hjQGo5KSXRxbL/47X3rmMw==",
+      "dev": true,
+      "bin": {
+        "md5-file": "cli.js"
+      },
+      "engines": {
+        "node": ">=10.13.0"
+      }
+    },
+    "node_modules/requirejs": {
+      "version": "2.3.6",
+      "resolved": "https://registry.npmjs.org/requirejs/-/requirejs-2.3.6.tgz",
+      "integrity": "sha512-ipEzlWQe6RK3jkzikgCupiTbTvm4S0/CAU5GlgptkN5SO6F3u0UD0K18wy6ErDqiCyP4J4YYe1HuAShvsxePLg==",
+      "bin": {
+        "r_js": "bin/r.js",
+        "r.js": "bin/r.js"
+      },
+      "engines": {
+        "node": ">=0.4.0"
+      }
+    },
+    "node_modules/source-map": {
+      "version": "0.6.1",
+      "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz",
+      "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==",
+      "engines": {
+        "node": ">=0.10.0"
+      }
+    },
+    "node_modules/source-map-support": {
+      "version": "0.5.19",
+      "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.19.tgz",
+      "integrity": "sha512-Wonm7zOCIJzBGQdB+thsPar0kYuCIzYvxZwlBa87yi/Mdjv7Tip2cyVbLj5o0cFPN4EVkuTwb3GDDyUx2DGnGw==",
+      "dependencies": {
+        "buffer-from": "^1.0.0",
+        "source-map": "^0.6.0"
+      }
+    },
+    "node_modules/terser": {
+      "version": "5.6.0-beta",
+      "resolved": "https://registry.npmjs.org/terser/-/terser-5.6.0-beta.tgz",
+      "integrity": "sha512-XqPZwi17FkFr42a6eGITU4ZHPixz1ZmuM9URQ/waMwxHenKjrxPndHtnuhNJ399P8tWFQuzZTTdN4ce3e2s28Q==",
+      "dependencies": {
+        "commander": "^2.20.0",
+        "source-map": "~0.7.2",
+        "source-map-support": "~0.5.19"
+      },
+      "bin": {
+        "terser": "bin/terser"
+      },
+      "engines": {
+        "node": ">=10"
+      }
+    },
+    "node_modules/terser/node_modules/source-map": {
+      "version": "0.7.3",
+      "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.3.tgz",
+      "integrity": "sha512-CkCj6giN3S+n9qrYiBTX5gystlENnRW5jZeNLHpe6aue+SrHcG5VYwujhW9s4dY31mEGsxBDrHR6oI69fTXsaQ==",
+      "engines": {
+        "node": ">= 8"
+      }
+    },
+    "node_modules/ts-node": {
+      "version": "8.10.2",
+      "resolved": "https://registry.npmjs.org/ts-node/-/ts-node-8.10.2.tgz",
+      "integrity": "sha512-ISJJGgkIpDdBhWVu3jufsWpK3Rzo7bdiIXJjQc0ynKxVOVcg2oIrf2H2cejminGrptVc6q6/uynAHNCuWGbpVA==",
+      "dependencies": {
+        "arg": "^4.1.0",
+        "diff": "^4.0.1",
+        "make-error": "^1.1.1",
+        "source-map-support": "^0.5.17",
+        "yn": "3.1.1"
+      },
+      "bin": {
+        "ts-node": "dist/bin.js",
+        "ts-node-script": "dist/bin-script.js",
+        "ts-node-transpile-only": "dist/bin-transpile.js",
+        "ts-script": "dist/bin-script-deprecated.js"
+      },
+      "engines": {
+        "node": ">=6.0.0"
+      }
+    },
+    "node_modules/typescript": {
+      "version": "4.0.2",
+      "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.0.2.tgz",
+      "integrity": "sha512-e4ERvRV2wb+rRZ/IQeb3jm2VxBsirQLpQhdxplZ2MEzGvDkkMmPglecnNDfSUBivMjP93vRbngYYDQqQ/78bcQ==",
+      "dev": true,
+      "bin": {
+        "tsc": "bin/tsc",
+        "tsserver": "bin/tsserver"
+      },
+      "engines": {
+        "node": ">=4.2.0"
+      }
+    },
+    "node_modules/yn": {
+      "version": "3.1.1",
+      "resolved": "https://registry.npmjs.org/yn/-/yn-3.1.1.tgz",
+      "integrity": "sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==",
+      "engines": {
+        "node": ">=6"
+      }
+    }
+  },
   "dependencies": {
     "@types/md5-file": {
       "version": "4.0.2",
       "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz",
       "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A=="
     },
+    "commander": {
+      "version": "2.20.3",
+      "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz",
+      "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ=="
+    },
+    "deepmerge": {
+      "version": "4.2.2",
+      "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.2.2.tgz",
+      "integrity": "sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg=="
+    },
     "diff": {
       "version": "4.0.2",
       "resolved": "https://registry.npmjs.org/diff/-/diff-4.0.2.tgz",
         "source-map": "^0.6.0"
       }
     },
+    "terser": {
+      "version": "5.6.0-beta",
+      "resolved": "https://registry.npmjs.org/terser/-/terser-5.6.0-beta.tgz",
+      "integrity": "sha512-XqPZwi17FkFr42a6eGITU4ZHPixz1ZmuM9URQ/waMwxHenKjrxPndHtnuhNJ399P8tWFQuzZTTdN4ce3e2s28Q==",
+      "requires": {
+        "commander": "^2.20.0",
+        "source-map": "~0.7.2",
+        "source-map-support": "~0.5.19"
+      },
+      "dependencies": {
+        "source-map": {
+          "version": "0.7.3",
+          "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.3.tgz",
+          "integrity": "sha512-CkCj6giN3S+n9qrYiBTX5gystlENnRW5jZeNLHpe6aue+SrHcG5VYwujhW9s4dY31mEGsxBDrHR6oI69fTXsaQ=="
+        }
+      }
+    },
     "ts-node": {
       "version": "8.10.2",
       "resolved": "https://registry.npmjs.org/ts-node/-/ts-node-8.10.2.tgz",
       "integrity": "sha512-e4ERvRV2wb+rRZ/IQeb3jm2VxBsirQLpQhdxplZ2MEzGvDkkMmPglecnNDfSUBivMjP93vRbngYYDQqQ/78bcQ==",
       "dev": true
     },
-    "uglify-js": {
-      "version": "3.10.1",
-      "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.10.1.tgz",
-      "integrity": "sha512-RjxApKkrPJB6kjJxQS3iZlf///REXWYxYJxO/MpmlQzVkDWVI3PSnCBWezMecmTU/TRkNxrl8bmsfFQCp+LO+Q=="
-    },
     "yn": {
       "version": "3.1.1",
       "resolved": "https://registry.npmjs.org/yn/-/yn-3.1.1.tgz",
index df5267d164882376167da821207a91247e9482b3..2f1011f69efd714819e49ed04f865d2ae5266b9e 100644 (file)
@@ -1,8 +1,9 @@
 {
   "dependencies": {
+    "deepmerge": "^4.2.2",
     "requirejs": "^2.3.6",
-    "ts-node": "^8.10.2",
-    "uglify-js": "^3.10.1"
+    "terser": "^5.6.0-beta",
+    "ts-node": "^8.10.2"
   },
   "devDependencies": {
     "@types/md5-file": "^4.0.2",