简体   繁体   中英

How to deal with external modules when compiling TypeScript?

I am very new to TypeScript and I am trying out many things and got stuck with external modules after compilation.

I started with simple TypeScript project in Visual Studio Code set to target ES2015 and module to es2015 (because I want to use native stuff as much as possible) and I wanted to try Strongly Type Events (STE) which I installed using npm.

By changing module resolution to node and setting baseUrl in tsconfig.json , TypeScript has no problem in using STE with non-relative import:

import { SimpleEventDispatcher } from "ste-simple-events";

However, when I compile TypeScript, resulting JavaScript file has exact same import statement and when loading html which is including this module, I get an error that module cannot be found.

I can not figure out how to solve this. Should TypeScript somehow change import statement to exact location of STE? Perhaps, but TypeScript team says TypeScript compilation will never change code in import statements.

Or should I somehow compile external modules as well, so that they get included in output?

Or should default module resolution in ES2015 standard implemented in browsers do the job - for which I have no idea how it works and how should external ES2015 modules be imported in JavaScript?

Any help or a nudge in the right direction would be greatly appreciated.

Thanks, Mario

For any TypeScript beginner scratching their head over this, the answer is called JavaScript bundlers.

Since I am using ES6, I opted for RollupJs bundler combined with following plugins (use them in this order):

  1. rollup-plugin-resolve - required to resolve node_modules
  2. rollup-plugin-commonjs - required to transpile CommonJS modules in node_modules to ES6
  3. rollup-plugin-typescript2 - optional, you can have it in the process or you can use tsc manually before you run rollup - just make sure you use version 2 (first version is not maintained any more)
  4. rollup-plugin-terser - minifier and obfuscator

You can install all of those with npm: npm install rollup rollup-plugin-resolve rollup-plugin-commonjs rollup-plugin-typescript2 rollup-plugin-terser

Add rollup.config.js to the root of your project, mine looked like this:

    import typescript from "rollup-plugin-typescript2"
    import commonjs from "rollup-plugin-commonjs";
    import resolve from "rollup-plugin-node-resolve";
    import { terser } from "rollup-plugin-terser";
    import pkg from "./package.json"

    export default {
        input: "./wwwroot/js/svgts.js",
        output: [
            {
                file: pkg.module,
                format: "esm",
            },
        ],
        external: [
            ...Object.keys(pkg.dependencies || {}),
            ...Object.keys(pkg.peerDependencies || {}),
        ], plugins: [
            resolve({
                mainFields: ["module"], // Default: ["module", "main"]
            }),

            commonjs({
                include: "node_modules/**"
            }),

            typescript({
                typescript: require("typescript"),
                tsconfig: "./tsconfig.json"
            }),

            (process.env.NODE_ENV === "production" && terser({
                mangle: { reserved: ['svg'] }
            }))
        ],
    }

Rollup supports environment variables which I use here with line: process.env.NODE_ENV === "production"

This allows you to create npm scripts in package.json to easily include minification or not, for example:

"scripts": {
    "tsc": "tsc",
    "tsc:w": "tsc -w",
    "lite": "lite-server",
    "rollup": "rollup -c",
    "rollupw": "rollup -cw",
    "start": "concurrently \"npm run rollupw\" \"npm run lite\"",
    "startprod": "NODE_ENV=production concurrently \"npm run rollupw\" \"npm run lite\"",
    "production": "NODE_ENV=production npm run rollup"
  },

Then you can run in terminal npm run production for instance to build minified bundle.

You can find more details on GitHub of each project.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM