├── .github
├── CODEOWNERS
├── dependabot.yml
└── workflows
│ ├── ci.yml
│ └── pr.yml
├── .gitignore
├── CODE_OF_CONDUCT.md
├── LICENSE
├── dist
├── ncc
│ ├── buildin
│ │ └── readme.md
│ ├── loaders
│ │ └── readme.md
│ └── readme.md
└── readme.md
├── examples
├── hello-world
│ ├── README.md
│ ├── index.js
│ └── package.json
├── multiple-bundles
│ ├── README.md
│ ├── cli.js
│ ├── main.js
│ ├── main.test.js
│ └── package.json
├── programmatic
│ ├── README.md
│ ├── package.json
│ ├── scripts
│ │ └── build.js
│ └── src
│ │ ├── __dev__.js
│ │ ├── routes
│ │ ├── cat.js
│ │ ├── dog.js
│ │ └── fox.js
│ │ └── utils.js
└── typescript
│ ├── README.md
│ ├── index.ts
│ ├── package.json
│ └── tsconfig.json
├── jest.config.js
├── package-support.md
├── package.json
├── readme.md
├── release.config.js
├── scripts
└── build.js
├── src
├── @@notfound.js
├── cli.js
├── index.js
├── loaders
│ ├── empty-loader.js
│ ├── notfound-loader.js
│ ├── relocate-loader.js
│ ├── shebang-loader.js
│ ├── stringify-loader.js
│ ├── ts-loader.js
│ └── uncacheable.js
├── sourcemap-register.js.cache.js
├── typescript.js
└── utils
│ ├── get-package-base.js
│ ├── has-type-module.js
│ ├── ncc-cache-dir.js
│ └── shebang.js
├── test
├── binary
│ ├── binding.gyp
│ └── hello.cc
├── cli.js
├── cli.test.js
├── fixtures
│ ├── error.js
│ ├── index.html
│ ├── interop-test.mjs
│ ├── interop.cjs
│ ├── module.cjs
│ ├── no-dep.js
│ ├── sourcemap-resource-path
│ │ ├── index.ts
│ │ ├── sum.ts
│ │ └── tsconfig.json
│ ├── test.cjs
│ ├── test.mjs
│ ├── ts-error1
│ │ ├── fail.ts
│ │ └── tsconfig.json
│ ├── ts-error2
│ │ ├── ts-error.ts
│ │ └── tsconfig.json
│ ├── ts-interop
│ │ ├── interop.ts
│ │ └── tsconfig.json
│ ├── type-module
│ │ ├── main.js
│ │ └── package.json
│ └── with-type-errors
│ │ ├── ts-error.ts
│ │ └── tsconfig.json
├── integration.test.js
├── integration
│ ├── analytics-node.js
│ ├── apollo.js
│ ├── auth0.js
│ ├── aws-sdk.js
│ ├── axios.js
│ ├── azure-cosmos.js
│ ├── azure-storage.js
│ ├── binary-require.js
│ ├── browserify-middleware.js
│ ├── bugsnag-js.js
│ ├── canvas.js
│ ├── chromeless.js
│ ├── core-js.js
│ ├── cowsay.js
│ ├── env-var.js
│ ├── es-module.js
│ ├── esm.js
│ ├── express-consolidate.js
│ ├── express.js
│ ├── fetch-h2.js
│ ├── ffmpeg.js
│ ├── firebase-admin.js
│ ├── firebase.js
│ ├── firestore.js
│ ├── fluent-ffmpeg.js
│ ├── google-bigquery.js
│ ├── got.js
│ ├── hot-shots.js
│ ├── include
│ │ └── throwing.js
│ ├── ioredis.js
│ ├── isomorphic-unfetch.js
│ ├── jimp.js
│ ├── json-without-ext-sample.json
│ ├── json-without-ext.js
│ ├── jugglingdb.js
│ ├── koa.js
│ ├── leveldown.js
│ ├── lighthouse.js
│ ├── loopback.js
│ ├── mailgun.js
│ ├── mariadb.js
│ ├── memcached.js
│ ├── mongoose.js
│ ├── mysql.js
│ ├── node-path
│ │ └── foo.js
│ ├── node_modules
│ │ ├── node_gyp
│ │ │ ├── noop.js
│ │ │ └── package.json
│ │ └── typescript
│ │ │ ├── index.js
│ │ │ └── lib
│ ├── notfound-eval.js
│ ├── npm.js
│ ├── oracledb.js
│ ├── passport.js
│ ├── path-platform.js
│ ├── pdfkit.js
│ ├── pg.js
│ ├── pug.js
│ ├── react.js
│ ├── redis.js
│ ├── request-ts.ts
│ ├── request.js
│ ├── rxjs.js
│ ├── saslprep.js
│ ├── sentry.js
│ ├── sequelize.js
│ ├── sharp.js
│ ├── slack.js
│ ├── socket.io.js
│ ├── stack-trace.js
│ ├── strict-module-exception-handling.js
│ ├── stripe.js
│ ├── test.ts
│ ├── tiny-json-http.js
│ ├── tsconfig.json
│ ├── twilio.js
│ ├── vm2.js
│ ├── vue.js
│ └── when.js
├── unit.test.js
├── unit
│ ├── browser-mainfield
│ │ ├── input.js
│ │ ├── node_modules
│ │ │ └── crypto-browser
│ │ │ │ ├── browser.js
│ │ │ │ ├── node.js
│ │ │ │ └── package.json
│ │ ├── opt.json
│ │ ├── output-coverage.js
│ │ └── output.js
│ ├── bundle-subasset
│ │ ├── input.js
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ ├── pi-bridge.js
│ │ ├── pi.ts
│ │ └── tsconfig.json
│ ├── bundle-subasset2
│ │ ├── input.ts
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ ├── pi-bridge.js
│ │ ├── pi.ts
│ │ └── tsconfig.json
│ ├── custom-emit
│ │ ├── input.js
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ └── test.json
│ ├── double-nested-builds
│ │ ├── input.js
│ │ ├── output-coverage.js
│ │ └── output.js
│ ├── exports-nomodule
│ │ ├── input.js
│ │ ├── no.js
│ │ ├── node.js
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ └── package.json
│ ├── exports-wildcard
│ │ ├── input.js
│ │ ├── no.js
│ │ ├── node.js
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ └── package.json
│ ├── externals
│ │ ├── input.js
│ │ ├── output-coverage.js
│ │ └── output.js
│ ├── import-meta-esm
│ │ ├── input.js
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ └── package.json
│ ├── imports
│ │ ├── input.js
│ │ ├── no.js
│ │ ├── node.js
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ └── package.json
│ ├── minify-err
│ │ ├── input.js
│ │ ├── opt.json
│ │ ├── output-coverage.js
│ │ └── output.js
│ ├── minify-sourcemap-register
│ │ ├── input.js
│ │ ├── opt.json
│ │ ├── output-coverage.js
│ │ ├── output-coverage.js.map
│ │ ├── output.js
│ │ └── output.js.map
│ ├── minify-v8cache-sourcemap-register
│ │ ├── input.js
│ │ ├── opt.json
│ │ ├── output-coverage.js
│ │ ├── output-coverage.js.map
│ │ ├── output.js
│ │ └── output.js.map
│ ├── minify
│ │ ├── input.js
│ │ ├── opt.json
│ │ ├── output-coverage.js
│ │ ├── output-coverage.js.map
│ │ ├── output.js
│ │ └── output.js.map
│ ├── nested-builds
│ │ ├── input.js
│ │ ├── output-coverage.js
│ │ └── output.js
│ ├── runtime-notfound
│ │ ├── input.js
│ │ ├── output-coverage.js
│ │ └── output.js
│ ├── shebang
│ │ ├── input.js
│ │ ├── output-coverage.js
│ │ └── output.js
│ ├── ts-decl-dir
│ │ ├── input.js
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ ├── test.ts
│ │ └── tsconfig.json
│ ├── ts-decl
│ │ ├── input.js
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ ├── test.ts
│ │ └── tsconfig.json
│ ├── ts-exts
│ │ ├── dep-dep.ts
│ │ ├── dep.ts
│ │ ├── input.ts
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ └── tsconfig.json
│ ├── ts-mixed-modules
│ │ ├── input.ts
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ ├── tsconfig.json
│ │ └── types.ts
│ ├── ts-target-es2018
│ │ ├── input.ts
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ └── tsconfig.json
│ ├── tsconfig-paths-allowjs
│ │ ├── input.ts
│ │ ├── module.js
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ └── tsconfig.json
│ ├── tsconfig-paths-array-extends
│ │ ├── input.ts
│ │ ├── module.js
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ ├── tsconfig.a.json
│ │ ├── tsconfig.b.json
│ │ └── tsconfig.json
│ ├── tsconfig-paths-conflicting-external
│ │ ├── input.ts
│ │ ├── module.ts
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ └── tsconfig.json
│ └── tsconfig-paths
│ │ ├── input.ts
│ │ ├── module.ts
│ │ ├── output-coverage.js
│ │ ├── output.js
│ │ └── tsconfig.json
└── watcher.test.js
├── update-fixtures.sh
└── yarn.lock
/.github/CODEOWNERS:
--------------------------------------------------------------------------------
1 | * @styfle @Timer
2 |
--------------------------------------------------------------------------------
/.github/dependabot.yml:
--------------------------------------------------------------------------------
1 | version: 2
2 | updates:
3 | - package-ecosystem: github-actions
4 | directory: /
5 | schedule:
6 | interval: monthly
7 | - package-ecosystem: npm
8 | directory: /
9 | schedule:
10 | interval: monthly
11 |
--------------------------------------------------------------------------------
/.github/workflows/ci.yml:
--------------------------------------------------------------------------------
1 | name: CI
2 |
3 | on:
4 | push:
5 | branches:
6 | - main
7 | tags:
8 | - '!*'
9 | pull_request:
10 |
11 | concurrency:
12 | group: ${{ github.workflow }}-${{ github.ref }}
13 | cancel-in-progress: ${{ github.ref != 'refs/heads/main' }}
14 |
15 | jobs:
16 | test:
17 | name: Node ${{ matrix.node }} and ${{ matrix.os }}
18 | timeout-minutes: 30
19 | strategy:
20 | fail-fast: false
21 | matrix:
22 | os: [ubuntu-latest, macos-latest, windows-latest]
23 | node: [18, 20]
24 | runs-on: ${{ matrix.os }}
25 | steps:
26 | - uses: actions/checkout@v4
27 | # https://github.com/nodejs/node-gyp#installation
28 | - name: Use Python 3.11
29 | uses: actions/setup-python@v5
30 | with:
31 | python-version: '3.11'
32 | # https://github.com/hargasinski/node-canvas/blob/e7abe64833d13ec96449c827b1e14befbdf3105d/.github/workflows/ci.yaml#L70
33 | - name: "macOS dependencies"
34 | if: matrix.os == 'macos-latest'
35 | run: |
36 | brew update
37 | brew install pkg-config cairo pango libpng jpeg giflib librsvg
38 | # https://github.com/hargasinski/node-canvas/blob/e7abe64833d13ec96449c827b1e14befbdf3105d/.github/workflows/ci.yaml#L25
39 | - name: "GNU/Linux dependencies"
40 | if: matrix.os == 'ubuntu-latest'
41 | run: |
42 | sudo apt update
43 | sudo apt install -y libcairo2-dev libjpeg-dev libpango1.0-dev libgif-dev librsvg2-dev
44 | - name: Use Node.js ${{ matrix.node }}
45 | uses: actions/setup-node@v4
46 | with:
47 | cache: yarn
48 | node-version: ${{ matrix.node }}
49 | check-latest: true
50 | - name: Install Dependencies
51 | run: yarn global add node-gyp && yarn install --frozen-lockfile
52 | - name: Build Test Binary
53 | run: yarn build-test-binary
54 | - name: Build
55 | run: yarn build
56 | - name: Run Tests
57 | run: yarn test
58 | - name: Coverage
59 | if: matrix.os == 'ubuntu-latest' && matrix.node == 20 # only run once
60 | run: yarn test-coverage
61 | - name: Maybe Release
62 | if: matrix.os == 'ubuntu-latest' && matrix.node == 20 && github.event_name == 'push' && github.ref == 'refs/heads/main'
63 | env:
64 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
65 | NPM_TOKEN: ${{ secrets.NPM_TOKEN_ELEVATED }}
66 | run: npx semantic-release@19.0.5
67 |
--------------------------------------------------------------------------------
/.github/workflows/pr.yml:
--------------------------------------------------------------------------------
1 | name: PR
2 | on:
3 | pull_request:
4 | types: [opened, edited, synchronize]
5 | pull_request_target:
6 | types: [opened, edited, synchronize]
7 |
8 | jobs:
9 | lint:
10 | runs-on: ubuntu-latest
11 | steps:
12 | - uses: amannn/action-semantic-pull-request@0723387faaf9b38adef4775cd42cfd5155ed6017
13 | env:
14 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
15 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | *
2 | dist/**/*.js
3 | !scripts
4 | !src
5 | !src/*.js
6 | !test
7 | !test/integration
8 | !test/integration/*.json
9 | !test/integration/*.js
10 | !test/integration/*.ts
11 | !test/integration/include/
12 | !test/integration/include/*.js
13 | !test/integration/node-path
14 | !test/integration/node-path/*.js
15 | !test/unit
16 | !test/unit/**
17 | !dist/
18 | !dist/ncc/
19 | !dist/buildin/
20 | !package.json
21 | !yarn.lock
22 | !.circleci
23 | !.github
24 | !.github/
25 | !.github/**
26 | !release.config.js
27 | !.*ignore
28 | !readme.md
29 | !examples/
30 | !examples/**
31 | examples/**/node_modules
32 | examples/**/dist
33 |
--------------------------------------------------------------------------------
/CODE_OF_CONDUCT.md:
--------------------------------------------------------------------------------
1 | ## Code of Conduct
2 |
3 | ### Our Pledge
4 |
5 | In the interest of fostering an open and welcoming environment, we as
6 | contributors and maintainers pledge to making participation in our project and
7 | our community a harassment-free experience for everyone, regardless of age, body
8 | size, disability, ethnicity, gender identity and expression, level of experience,
9 | nationality, personal appearance, race, religion, or sexual identity and
10 | orientation.
11 |
12 | ### Our Standards
13 |
14 | Examples of behavior that contributes to creating a positive environment
15 | include:
16 |
17 | - Using welcoming and inclusive language
18 | - Being respectful of differing viewpoints and experiences
19 | - Gracefully accepting constructive criticism
20 | - Focusing on what is best for the community
21 | - Showing empathy towards other community members
22 |
23 | Examples of unacceptable behavior by participants include:
24 |
25 | - The use of sexualized language or imagery and unwelcome sexual attention or
26 | advances
27 | - Trolling, insulting/derogatory comments, and personal or political attacks
28 | - Public or private harassment
29 | - Publishing others' private information, such as a physical or electronic
30 | address, without explicit permission
31 | - Other conduct which could reasonably be considered inappropriate in a
32 | professional setting
33 |
34 | ### Our Responsibilities
35 |
36 | Project maintainers are responsible for clarifying the standards of acceptable
37 | behavior and are expected to take appropriate and fair corrective action in
38 | response to any instances of unacceptable behavior.
39 |
40 | Project maintainers have the right and responsibility to remove, edit, or
41 | reject comments, commits, code, wiki edits, issues, and other contributions
42 | that are not aligned to this Code of Conduct, or to ban temporarily or
43 | permanently any contributor for other behaviors that they deem inappropriate,
44 | threatening, offensive, or harmful.
45 |
46 | ### Scope
47 |
48 | This Code of Conduct applies both within project spaces and in public spaces
49 | when an individual is representing the project or its community. Examples of
50 | representing a project or community include using an official project e-mail
51 | address, posting via an official social media account, or acting as an appointed
52 | representative at an online or offline event. Representation of a project may be
53 | further defined and clarified by project maintainers.
54 |
55 | ### Enforcement
56 |
57 | Instances of abusive, harassing, or otherwise unacceptable behavior may be
58 | reported by contacting the project team at [abuse@zeit.co](mailto:abuse@zeit.co). All
59 | complaints will be reviewed and investigated and will result in a response that
60 | is deemed necessary and appropriate to the circumstances. The project team is
61 | obligated to maintain confidentiality with regard to the reporter of an incident.
62 | Further details of specific enforcement policies may be posted separately.
63 |
64 | Project maintainers who do not follow or enforce the Code of Conduct in good
65 | faith may face temporary or permanent repercussions as determined by other
66 | members of the project's leadership.
67 |
68 | ### Attribution
69 |
70 | This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4,
71 | available at [http://contributor-covenant.org/version/1/4][version]
72 |
73 | [homepage]: http://contributor-covenant.org
74 | [version]: http://contributor-covenant.org/version/1/4/
75 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | Copyright 2018 ZEIT, Inc.
2 |
3 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
4 |
5 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
6 |
7 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
--------------------------------------------------------------------------------
/dist/ncc/buildin/readme.md:
--------------------------------------------------------------------------------
1 | # About this directory
2 |
3 | This directory will contain the webpack built-ins, like
4 | `module.js`, so that they can be accessed by webpack when
5 | it's being executed inside the bundled ncc file.
6 |
7 | These files are published to npm.
8 |
--------------------------------------------------------------------------------
/dist/ncc/loaders/readme.md:
--------------------------------------------------------------------------------
1 | # About this directory
2 |
3 | This directory will contain:
4 |
5 | - `relocate-loader.js` the ncc loader for handling CommonJS asset and reference relocations
6 | - `shebang-loader.js` the ncc loader to ensure proper hash bang support in Node.js CLI files
7 | - `ts-loader.js` the ncc loader for handling TypeScript
8 |
9 | These are generated by the `build` step defined in `../../../package.json`.
10 |
11 | These files are published to npm.
12 |
--------------------------------------------------------------------------------
/dist/ncc/readme.md:
--------------------------------------------------------------------------------
1 | # About this directory
2 |
3 | This directory will contain:
4 |
5 | - `index.js` the main ncc bundle
6 | - `cli.js` the CLI bundle, excluding the main ncc bundle
7 | - `typescript.js` the TypeScript detection file
8 |
9 | These are generated by the `build` step defined in `../../package.json`.
10 |
11 | These files are published to npm.
12 |
--------------------------------------------------------------------------------
/dist/readme.md:
--------------------------------------------------------------------------------
1 | # About this directory
2 |
3 | This directory will contain:
4 | - `buildin`: the webpack `buildin/` folder, required at runtime
5 | - `ncc`: the output from the ncc build
6 |
7 | They are generated by the `build` script defined in `../package.json`.
8 |
9 | This directory is the only one published to npm.
10 |
--------------------------------------------------------------------------------
/examples/hello-world/README.md:
--------------------------------------------------------------------------------
1 | # Hello World
2 |
3 | ## How to use
4 |
5 | Within this directory, run `yarn` to install dependencies.
6 |
7 | To execute the Node.js program with `ncc`, run `yarn dev`.
8 |
9 | To build the program with `ncc`, run `yarn build`.
10 |
--------------------------------------------------------------------------------
/examples/hello-world/index.js:
--------------------------------------------------------------------------------
1 | const chalk = require("chalk");
2 |
3 | console.log(chalk.green("Hello World!"));
4 |
--------------------------------------------------------------------------------
/examples/hello-world/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "hello-world",
3 | "private": true,
4 | "version": "0.0.0",
5 | "license": "MIT",
6 | "scripts": {
7 | "dev": "ncc run index.js",
8 | "build": "ncc build index.js -o dist"
9 | },
10 | "dependencies": {
11 | "chalk": "^2.4.1"
12 | },
13 | "devDependencies": {
14 | "@vercel/ncc": "latest"
15 | }
16 | }
17 |
--------------------------------------------------------------------------------
/examples/multiple-bundles/README.md:
--------------------------------------------------------------------------------
1 | # Multiple Bundles
2 |
3 | This example shows how you could build a simple module along with a CLI.
4 |
5 | ## How to use
6 |
7 | Within this directory, run `yarn` to install dependencies.
8 |
9 | To build the main module, run `yarn build:main`. You'll notice the resulting `dist/main/index.js` only includes `main.js` and its `chalk` dependency.
10 |
11 | To build the CLI, run `yarn build:cli`. You'll notice the resulting `dist/cli/index.js` includes its `args` dependency in addition to everything required for `main.js`.
12 |
13 | _To build both concurrently, run `yarn build`._
14 |
15 | To test the main module, run `yarn test`. You'll notice it uses a `strip-ansi` dependency that is not included in any of the builds.
16 |
17 | To use the built CLI, run `./dist/cli/index.js color` or `./dist/cli/index.js number`. If this were published to npm as "lucky", you would be able to run `lucky color` or `lucky number` because of the `bin` declaration in `package.json`.
18 |
--------------------------------------------------------------------------------
/examples/multiple-bundles/cli.js:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env node
2 |
3 | const args = require("args");
4 |
5 | const { color, number } = require("./main");
6 |
7 | args
8 | .command("color", "Receive a lucky color", () => {
9 | console.log(color());
10 | })
11 | .command("number", "Receive a lucky number", () => {
12 | console.log(number());
13 | });
14 |
15 | args.parse(process.argv, {
16 | name: "lucky"
17 | });
18 |
--------------------------------------------------------------------------------
/examples/multiple-bundles/main.js:
--------------------------------------------------------------------------------
1 | const chalk = require("chalk");
2 |
3 | exports.color = function color() {
4 | const color = Math.random() > 0.5 ? "red" : "blue";
5 |
6 | return `Your lucky color is ${chalk[color](color)}`;
7 | };
8 |
9 | exports.number = function number(min = 0, max = 100) {
10 | min = Math.ceil(min);
11 | max = Math.floor(max);
12 | //The maximum is exclusive and the minimum is inclusive
13 | const num = Math.floor(Math.random() * (max - min)) + min;
14 |
15 | return `Your lucky number is ${chalk.bold(num)}`;
16 | };
17 |
--------------------------------------------------------------------------------
/examples/multiple-bundles/main.test.js:
--------------------------------------------------------------------------------
1 | const assert = require("assert");
2 | const chalk = require("chalk");
3 | const stripAnsi = require("strip-ansi");
4 |
5 | const { color, number } = require("./main");
6 |
7 | function getValue(fn) {
8 | return stripAnsi(
9 | fn()
10 | .split(/\s/)
11 | .pop()
12 | );
13 | }
14 |
15 | // color is a function
16 | assert(typeof color === "function");
17 |
18 | // color is red or blue for this example
19 | const c = getValue(color);
20 | assert(c === "red" || c === "blue");
21 |
22 | // number is a function
23 | assert(typeof number === "function");
24 |
25 | // number returns an integer between 0 and 100 by default
26 | const n = getValue(number);
27 | assert(n > 0 && n <= 100);
28 |
29 | console.log(chalk.green("Tests pass!"));
30 |
--------------------------------------------------------------------------------
/examples/multiple-bundles/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "multiple-bundles",
3 | "private": true,
4 | "version": "0.0.0",
5 | "license": "MIT",
6 | "main": "./dist/main/index.js",
7 | "bin": {
8 | "lucky": "./dist/cli/index.js"
9 | },
10 | "scripts": {
11 | "build:cli": "ncc build cli.js -o dist/cli",
12 | "build:main": "ncc build main.js -o dist/main",
13 | "build": "concurrently 'npm:build:cli' 'npm:build:main'",
14 | "test": "node main.test.js"
15 | },
16 | "dependencies": {
17 | "args": "^5.0.0",
18 | "chalk": "^2.4.1"
19 | },
20 | "devDependencies": {
21 | "@vercel/ncc": "latest",
22 | "concurrently": "^4.1.0",
23 | "strip-ansi": "^5.0.0"
24 | }
25 | }
26 |
--------------------------------------------------------------------------------
/examples/programmatic/README.md:
--------------------------------------------------------------------------------
1 | # Programmatic
2 |
3 | This example shows how you can programmatically build multiple bundles. The build script (`scripts/build.js`) finds `.js` files in `src/routes/`, builds each one with `ncc`, and then writes the resulting file and its sourcemap to a new directory in `dist/`.
4 |
5 | ## How to use
6 |
7 | Within this directory, run `yarn` to install dependencies.
8 |
9 | To run a development server with `ncc`, run `yarn dev`. You can then test the routes:
10 |
11 | - [http://localhost:3000/cat]()
12 | - [http://localhost:3000/dog]()
13 | - [http://localhost:3000/fox]()
14 |
15 | To build all of the bundles, run `yarn build`.
16 |
17 | ```
18 | ❯ yarn build
19 | yarn run v1.12.3
20 | $ node ./scripts/build.js
21 | ✓ dist/dog/index.js (289.17KB)
22 | ✓ dist/dog/index.map.js (234.37KB)
23 | ✓ dist/fox/index.js (289.18KB)
24 | ✓ dist/fox/index.map.js (234.43KB)
25 | ✓ dist/cat/index.js (289.17KB)
26 | ✓ dist/cat/index.map.js (234.43KB)
27 | ✨ Done in 2.79s.
28 | ```
29 |
30 | Each subdirectory of `dist/` could be deployed to [a serverless environment](https://zeit.co/examples/nodejs/) to run independent of each other!
31 |
32 | ## Thanks
33 |
34 | Special thanks to [random.cat](http://random.cat/), [AdenFlorian/random.dog](https://github.com/AdenFlorian/random.dog), and [xinitrc-dev/randomfox.ca](https://github.com/xinitrc-dev/randomfox.ca) for their open APIs to make this example more fun and realistic!
35 |
--------------------------------------------------------------------------------
/examples/programmatic/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "programmatic",
3 | "private": true,
4 | "version": "0.0.0",
5 | "license": "MIT",
6 | "scripts": {
7 | "dev": "ncc run ./src/__dev__.js --watch",
8 | "build": "node ./scripts/build.js"
9 | },
10 | "dependencies": {
11 | "node-fetch": "^2.3.0"
12 | },
13 | "devDependencies": {
14 | "@vercel/ncc": "latest",
15 | "bytes": "^3.0.0",
16 | "glob": "^7.1.3",
17 | "mkdirp": "^0.5.1"
18 | }
19 | }
20 |
--------------------------------------------------------------------------------
/examples/programmatic/scripts/build.js:
--------------------------------------------------------------------------------
1 | const { statSync, writeFileSync } = require("fs");
2 | const { basename, relative, resolve } = require("path");
3 | const { promisify } = require("util");
4 |
5 | const bytes = require("bytes");
6 | const glob = promisify(require("glob"));
7 | const mkdirp = promisify(require("mkdirp"));
8 | const ncc = require("@vercel/ncc");
9 |
10 | // output directories
11 | const DIST_DIR = resolve(__dirname, "../dist");
12 | const CACHE_DIR = resolve(DIST_DIR, ".cache");
13 |
14 | // options for ncc with mix of defaults and customization
15 | const options = {
16 | // provide a custom cache path
17 | cache: CACHE_DIR,
18 | // externals to leave as requires of the build
19 | externals: [],
20 | minify: true,
21 | sourceMap: true,
22 | watch: false // default
23 | };
24 |
25 | // write file to disk and print final size
26 | function write(file, data) {
27 | writeFileSync(file, data);
28 |
29 | console.log(
30 | `✓ ${relative(__dirname + "/../", file)} (${bytes(statSync(file).size)})`
31 | );
32 | }
33 |
34 | // build file with its dependencies using ncc
35 | async function build(file) {
36 | const { code, map, assets } = await ncc(file, options);
37 |
38 | if (Object.keys(assets).length)
39 | console.error("New unexpected assets are being emitted for", file);
40 |
41 | const name = basename(file, ".js");
42 | await mkdirp(resolve(DIST_DIR, name));
43 | write(resolve(DIST_DIR, name, "index.js"), code);
44 | write(resolve(DIST_DIR, name, "index.map.js"), map);
45 | }
46 |
47 | async function main() {
48 | // create our output and custom cache directories
49 | await mkdirp(CACHE_DIR);
50 |
51 | // find all routes we want to bundle
52 | const files = await glob(resolve(__dirname, "../src/routes/*.js"));
53 |
54 | // build all found files
55 | return Promise.all(files.map(build));
56 | }
57 |
58 | main();
59 |
--------------------------------------------------------------------------------
/examples/programmatic/src/__dev__.js:
--------------------------------------------------------------------------------
1 | // Development server only intended to be used by `yarn dev`
2 |
3 | import { Server, STATUS_CODES } from "http";
4 | import { parse } from "url";
5 |
6 | import cat from "./routes/cat";
7 | import dog from "./routes/dog";
8 | import fox from "./routes/fox";
9 |
10 | const server = new Server(async (req, res) => {
11 | const { pathname } = parse(req.url);
12 |
13 | if (pathname === "/cat") return cat(req, res);
14 | if (pathname === "/dog") return dog(req, res);
15 | if (pathname === "/fox") return fox(req, res);
16 |
17 | res.writeHead(404);
18 | res.end(STATUS_CODES[404]);
19 | });
20 |
21 | const port = process.env.PORT || 3000;
22 |
23 | server.listen(port, () => {
24 | console.log(`Listening for HTTP requests on port ${port}...`);
25 | });
26 |
--------------------------------------------------------------------------------
/examples/programmatic/src/routes/cat.js:
--------------------------------------------------------------------------------
1 | import { animalAPI } from "../utils";
2 |
3 | export default (req, res) =>
4 | animalAPI(res, "Cat", "https://aws.random.cat/meow", "file");
5 |
--------------------------------------------------------------------------------
/examples/programmatic/src/routes/dog.js:
--------------------------------------------------------------------------------
1 | import { animalAPI } from "../utils";
2 |
3 | export default (req, res) =>
4 | animalAPI(res, "Dog", "https://random.dog/woof.json", "url");
5 |
--------------------------------------------------------------------------------
/examples/programmatic/src/routes/fox.js:
--------------------------------------------------------------------------------
1 | import { animalAPI } from "../utils";
2 |
3 | export default (req, res) =>
4 | animalAPI(res, "Fox", "https://randomfox.ca/floof/", "image");
5 |
--------------------------------------------------------------------------------
/examples/programmatic/src/utils.js:
--------------------------------------------------------------------------------
1 | import fetch from "node-fetch";
2 |
3 | export async function animalAPI(res, title, api, key) {
4 | const resp = await fetch(api);
5 | const json = await resp.json();
6 |
7 | const body = `
8 |
9 |
10 |
11 |
12 | ${title}
13 |
14 |
15 |
16 |
17 |
18 | `;
19 |
20 | res.writeHead(200, {
21 | "Content-Length": Buffer.byteLength(body),
22 | "Content-Type": "text/html; charset=utf-8"
23 | });
24 |
25 | res.end(body);
26 | }
27 |
--------------------------------------------------------------------------------
/examples/typescript/README.md:
--------------------------------------------------------------------------------
1 | # TypeScript
2 |
3 | ## How to use
4 |
5 | Within this directory, run `yarn` to install dependencies.
6 |
7 | To execute the Node.js program with `ncc`, run `yarn dev`.
8 |
9 | To build the program with `ncc`, run `yarn build`.
10 |
--------------------------------------------------------------------------------
/examples/typescript/index.ts:
--------------------------------------------------------------------------------
1 | import chalk from "chalk";
2 |
3 | function logSuccess(msg: string) {
4 | console.log(chalk.green(msg));
5 | }
6 |
7 | logSuccess("Hello World!");
8 |
--------------------------------------------------------------------------------
/examples/typescript/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "typescript",
3 | "private": true,
4 | "version": "0.0.0",
5 | "license": "MIT",
6 | "scripts": {
7 | "dev": "ncc run index.ts",
8 | "build": "ncc build index.ts -o dist"
9 | },
10 | "dependencies": {
11 | "chalk": "^2.4.1"
12 | },
13 | "devDependencies": {
14 | "@vercel/ncc": "latest",
15 | "typescript": "^4.4.2"
16 | }
17 | }
18 |
--------------------------------------------------------------------------------
/examples/typescript/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "compilerOptions": {
3 | "target": "es2015",
4 | "moduleResolution": "node"
5 | }
6 | }
7 |
--------------------------------------------------------------------------------
/jest.config.js:
--------------------------------------------------------------------------------
1 | module.exports = {
2 | collectCoverageFrom: ["src/**/*.js"],
3 | coverageReporters: ["html", "lcov"],
4 | testEnvironment: "node",
5 | testMatch: ["/test/**/*.test.js"]
6 | };
7 |
--------------------------------------------------------------------------------
/package-support.md:
--------------------------------------------------------------------------------
1 | ## ncc Package Configurations
2 |
3 | Packages that need specific configurations for ncc support are included below.
4 |
5 | If you are having trouble running a package with ncc, try searching for it in the [issue queue](https://github.com/zeit/ncc/issues) or posting an issue.
6 |
7 | ### `sequelize`
8 |
9 | For example, with the `mariadb` dialect:
10 |
11 | ```js
12 | const Sequelize = require('sequelize');
13 | const db = new Sequelize({
14 | dialect: 'mariadb',
15 | dialectModule: require('mariadb')
16 | });
17 | ```
18 |
19 | The important part here is defining `dialectModule`.
20 |
21 | ### `@google-cloud/vision`
22 |
23 | Add `google-proto-files` in your `package.json` dependencies.
24 |
25 | ```json
26 | {
27 | "name": "example",
28 | "main": "index.js",
29 | "dependencies": {
30 | "@google-cloud/vision": "1.1.1",
31 | "google-proto-files": "1.0.1"
32 | }
33 | }
34 | ```
35 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@vercel/ncc",
3 | "description": "Simple CLI for compiling a Node.js module into a single file, together with all its dependencies, gcc-style.",
4 | "version": "0.0.0-development",
5 | "repository": "vercel/ncc",
6 | "license": "MIT",
7 | "main": "./dist/ncc/index.js",
8 | "bin": {
9 | "ncc": "./dist/ncc/cli.js"
10 | },
11 | "files": [
12 | "dist"
13 | ],
14 | "scripts": {
15 | "build": "node scripts/build.js",
16 | "build-test-binary": "cd test/binary && node-gyp rebuild && cp build/Release/hello.node ../integration/hello.node",
17 | "test": "node --expose-gc --max_old_space_size=4096 node_modules/jest/bin/jest.js",
18 | "test-coverage": "node --expose-gc --max_old_space_size=4096 node_modules/jest/bin/jest.js --runInBand --coverage --globals \"{\\\"coverage\\\":true}\"",
19 | "prepublishOnly": "node scripts/build.js --no-cache"
20 | },
21 | "devDependencies": {
22 | "@aws-sdk/client-s3": "^3.787.0",
23 | "@azure/cosmos": "^3.17.3",
24 | "@bugsnag/js": "^7.21.0",
25 | "@ffmpeg-installer/ffmpeg": "^1.0.17",
26 | "@google-cloud/bigquery": "^5.7.0",
27 | "@google-cloud/firestore": "^6.7.0",
28 | "@sentry/node": "^7.66.0",
29 | "@slack/web-api": "^6.9.0",
30 | "@vercel/webpack-asset-relocator-loader": "1.7.3",
31 | "analytics-node": "^6.2.0",
32 | "apollo-server-express": "^2.2.2",
33 | "arg": "^5.0.2",
34 | "auth0": "^2.14.0",
35 | "axios": "^1.7.7",
36 | "azure-storage": "^2.10.2",
37 | "browserify-middleware": "^8.1.1",
38 | "bytes": "^3.1.2",
39 | "canvas": "3.0.0-rc2",
40 | "chromeless": "^1.5.2",
41 | "consolidate": "^0.16.0",
42 | "copy": "^0.3.2",
43 | "core-js": "^2.5.7",
44 | "cowsay": "^1.3.1",
45 | "esm": "^3.2.22",
46 | "express": "^4.18.2",
47 | "fetch-h2": "^3.0.2",
48 | "firebase": "^7.24.0",
49 | "firebase-admin": "^11.10.1",
50 | "fluent-ffmpeg": "^2.1.2",
51 | "fontkit": "^1.7.7",
52 | "get-folder-size": "^2.0.0",
53 | "glob": "^8.0.3",
54 | "got": "^12.5.2",
55 | "graceful-fs": "^4.2.11",
56 | "graphql": "^15.5.1",
57 | "hot-shots": "^8.5.0",
58 | "ioredis": "^5.3.2",
59 | "isomorphic-unfetch": "^4.0.2",
60 | "jest": "^27.5.1",
61 | "jimp": "^0.16.1",
62 | "jugglingdb": "2.0.1",
63 | "koa": "^2.14.2",
64 | "leveldown": "^6.0.0",
65 | "license-webpack-plugin": "^4.0.2",
66 | "lighthouse": "^8.1.0",
67 | "loopback": "^3.24.0",
68 | "mailgun": "^0.5.0",
69 | "mariadb": "^2.0.1-beta",
70 | "memcached": "^2.2.2",
71 | "memory-fs": "^0.5.0",
72 | "mkdirp": "^1.0.4",
73 | "mongoose": "^8.8.3",
74 | "mysql": "^2.16.0",
75 | "node-gyp": "^9.4.0",
76 | "npm": "^6.13.4",
77 | "oracledb": "^6.1.0",
78 | "passport": "^0.6.0",
79 | "passport-google-oauth": "^2.0.0",
80 | "path-platform": "^0.11.15",
81 | "pdfkit": "^0.13.0",
82 | "pg": "^8.11.3",
83 | "pug": "^3.0.1",
84 | "react": "^17.0.2",
85 | "react-dom": "^17.0.2",
86 | "redis": "^3.1.1",
87 | "request": "^2.88.0",
88 | "rxjs": "^7.8.1",
89 | "saslprep": "^1.0.2",
90 | "sequelize": "^6.32.1",
91 | "sharp": "^0.32.5",
92 | "shebang-loader": "^0.0.1",
93 | "socket.io": "^4.7.2",
94 | "source-map-support": "^0.5.9",
95 | "stripe": "^8.167.0",
96 | "swig": "^1.4.2",
97 | "terser": "^5.33.0",
98 | "the-answer": "^1.0.0",
99 | "tiny-json-http": "^7.5.1",
100 | "ts-loader": "^9.4.4",
101 | "tsconfig-paths": "^4.2.0",
102 | "tsconfig-paths-webpack-plugin": "^4.1.0",
103 | "twilio": "^3.23.2",
104 | "typescript": "^5.2.2",
105 | "vm2": "^3.9.19",
106 | "vue": "^2.5.17",
107 | "vue-server-renderer": "^2.5.17",
108 | "web-vitals": "^0.2.4",
109 | "webpack": "5.94.0",
110 | "when": "^3.7.8"
111 | },
112 | "packageManager": "yarn@1.22.22+sha512.a6b2f7906b721bba3d67d4aff083df04dad64c399707841b7acf00f6b133b7ac24255f2652fa22ae3534329dc6180534e98d17432037ff6fd140556e2bb3137e"
113 | }
114 |
--------------------------------------------------------------------------------
/readme.md:
--------------------------------------------------------------------------------
1 | # ncc
2 |
3 | [](https://github.com/vercel/ncc/actions?workflow=CI)
4 |
5 | Simple CLI for compiling a Node.js module into a single file,
6 | together with all its dependencies, gcc-style.
7 |
8 | ## Motivation
9 |
10 | - Publish minimal packages to npm
11 | - Only ship relevant app code to serverless environments
12 | - Don't waste time configuring bundlers
13 | - Generally faster bootup time and less I/O overhead
14 | - Compiled language-like experience (e.g.: `go`)
15 |
16 | ## Design goals
17 |
18 | - Zero configuration
19 | - TypeScript built-in
20 | - Only supports Node.js programs as input / output
21 | - Support all Node.js patterns and npm modules
22 |
23 | ## Usage
24 |
25 | ### Installation
26 | ```bash
27 | npm i -g @vercel/ncc
28 | ```
29 |
30 | ### Usage
31 |
32 | ```bash
33 | $ ncc
34 | ```
35 | Eg:
36 | ```bash
37 | $ ncc build input.js -o dist
38 | ```
39 |
40 | If building an `.mjs` or `.js` module inside a `"type": "module"` [package boundary](https://nodejs.org/dist/latest-v16.x/docs/api/packages.html#packages_package_json_and_file_extensions), an ES module output will be created automatically.
41 |
42 | Outputs the Node.js compact build of `input.js` into `dist/index.js`.
43 |
44 | > Note: If the input file is using a `.cjs` extension, then so will the corresponding output file.
45 | > This is useful for packages that want to use `.js` files as modules in native Node.js using
46 | > a `"type": "module"` in the package.json file.
47 |
48 | #### Commands:
49 | ```
50 | build [opts]
51 | run [opts]
52 | cache clean|dir|size
53 | help
54 | version
55 | ```
56 |
57 | #### Options:
58 | ```
59 | -o, --out [dir] Output directory for build (defaults to dist)
60 | -m, --minify Minify output
61 | -C, --no-cache Skip build cache population
62 | -s, --source-map Generate source map
63 | -a, --asset-builds Build nested JS assets recursively, useful for
64 | when code is loaded as an asset eg for workers.
65 | --no-source-map-register Skip source-map-register source map support
66 | -e, --external [mod] Skip bundling 'mod'. Can be used many times
67 | -q, --quiet Disable build summaries / non-error outputs
68 | -w, --watch Start a watched build
69 | -t, --transpile-only Use transpileOnly option with the ts-loader
70 | --v8-cache Emit a build using the v8 compile cache
71 | --license [file] Adds a file containing licensing information to the output
72 | --stats-out [file] Emit webpack stats as json to the specified output file
73 | --target [es] ECMAScript target to use for output (default: es2015)
74 | Learn more: https://webpack.js.org/configuration/target
75 | -d, --debug Show debug logs
76 | ```
77 |
78 | ### Execution Testing
79 |
80 | For testing and debugging, a file can be built into a temporary directory and executed with full source maps support with the command:
81 |
82 | ```bash
83 | $ ncc run input.js
84 | ```
85 |
86 | ### With TypeScript
87 |
88 | The only requirement is to point `ncc` to `.ts` or `.tsx` files. A `tsconfig.json`
89 | file is necessary. Most likely you want to indicate `es2015` support:
90 |
91 | ```json
92 | {
93 | "compilerOptions": {
94 | "target": "es2015",
95 | "moduleResolution": "node"
96 | }
97 | }
98 | ```
99 |
100 | If typescript is found in `devDependencies`, that version will be used.
101 |
102 | ### Package Support
103 |
104 | Some packages may need some extra options for ncc support in order to better work with the static analysis.
105 |
106 | See [package-support.md](package-support.md) for some common packages and their usage with ncc.
107 |
108 | ### Programmatically From Node.js
109 |
110 | ```js
111 | require('@vercel/ncc')('/path/to/input', {
112 | // provide a custom cache path or disable caching
113 | cache: "./custom/cache/path" | false,
114 | // externals to leave as requires of the build
115 | externals: ["externalpackage"],
116 | // directory outside of which never to emit assets
117 | filterAssetBase: process.cwd(), // default
118 | minify: false, // default
119 | sourceMap: false, // default
120 | assetBuilds: false, // default
121 | sourceMapBasePrefix: '../', // default treats sources as output-relative
122 | // when outputting a sourcemap, automatically include
123 | // source-map-support in the output file (increases output by 32kB).
124 | sourceMapRegister: true, // default
125 | watch: false, // default
126 | license: '', // default does not generate a license file
127 | target: 'es2015', // default
128 | v8cache: false, // default
129 | quiet: false, // default
130 | debugLog: false // default
131 | }).then(({ code, map, assets }) => {
132 | console.log(code);
133 | // Assets is an object of asset file names to { source, permissions, symlinks }
134 | // expected relative to the output code (if any)
135 | })
136 | ```
137 |
138 | When `watch: true` is set, the build object is not a promise, but has the following signature:
139 |
140 | ```js
141 | {
142 | // handler re-run on each build completion
143 | // watch errors are reported on "err"
144 | handler (({ err, code, map, assets }) => { ... })
145 | // handler re-run on each rebuild start
146 | rebuild (() => {})
147 | // close the watcher
148 | void close ();
149 | }
150 | ```
151 |
152 | ## Caveats
153 |
154 | - Files / assets are relocated based on a [static evaluator](https://github.com/vercel/webpack-asset-relocator-loader#how-it-works). Dynamic non-statically analyzable asset loads may not work out correctly
155 |
--------------------------------------------------------------------------------
/release.config.js:
--------------------------------------------------------------------------------
1 | module.exports = {
2 | branches: ['main'],
3 | tagFormat: '${version}',
4 | }
5 |
--------------------------------------------------------------------------------
/src/@@notfound.js:
--------------------------------------------------------------------------------
1 | module.exports = __non_webpack_require__('UNKNOWN');
2 |
--------------------------------------------------------------------------------
/src/loaders/empty-loader.js:
--------------------------------------------------------------------------------
1 | // returns the base-level package folder based on detecting "node_modules"
2 | // package name boundaries
3 | const pkgNameRegEx = /^(@[^\\\/]+[\\\/])?[^\\\/]+/;
4 | function getPackageBase(id) {
5 | const pkgIndex = id.lastIndexOf('node_modules');
6 | if (pkgIndex !== -1 &&
7 | (id[pkgIndex - 1] === '/' || id[pkgIndex - 1] === '\\') &&
8 | (id[pkgIndex + 12] === '/' || id[pkgIndex + 12] === '\\')) {
9 | const pkgNameMatch = id.substr(pkgIndex + 13).match(pkgNameRegEx);
10 | if (pkgNameMatch)
11 | return id.substr(0, pkgIndex + 13 + pkgNameMatch[0].length);
12 | }
13 | }
14 |
15 | const emptyModules = { 'uglify-js': true, 'uglify-es': true };
16 |
17 | module.exports = function (input, map) {
18 | const id = this.resourcePath;
19 | const pkgBase = getPackageBase(id);
20 | if (pkgBase) {
21 | const baseParts = pkgBase.split('/');
22 | if (baseParts[baseParts.length - 2] === 'node_modules') {
23 | const pkgName = baseParts[baseParts.length - 1];
24 | if (pkgName in emptyModules) {
25 | console.warn(`ncc: Ignoring build of ${pkgName}, as it is not statically analyzable. Build with "--external ${pkgName}" if this package is needed.`);
26 | return '';
27 | }
28 | }
29 | }
30 | this.callback(null, input, map);
31 | };
32 |
--------------------------------------------------------------------------------
/src/loaders/notfound-loader.js:
--------------------------------------------------------------------------------
1 | module.exports = function (input, map) {
2 | if (this.cacheable)
3 | this.cacheable();
4 | const id = this.resourceQuery.substr(1);
5 | input = input.replace('\'UNKNOWN\'', JSON.stringify(id));
6 | this.callback(null, input, map);
7 | };
8 |
--------------------------------------------------------------------------------
/src/loaders/relocate-loader.js:
--------------------------------------------------------------------------------
1 | module.exports = require('@vercel/webpack-asset-relocator-loader');
2 |
--------------------------------------------------------------------------------
/src/loaders/shebang-loader.js:
--------------------------------------------------------------------------------
1 | module.exports = require("shebang-loader");
2 |
--------------------------------------------------------------------------------
/src/loaders/stringify-loader.js:
--------------------------------------------------------------------------------
1 | module.exports = (source) => JSON.stringify(source);
2 |
--------------------------------------------------------------------------------
/src/loaders/ts-loader.js:
--------------------------------------------------------------------------------
1 | // we re-export so that we generate a unique
2 | // optional bundle for the ts-loader, that
3 | // doesn't get loaded unless the user is
4 | // compiling typescript
5 | const logger = require("ts-loader/dist/logger");
6 | const makeLogger = logger.makeLogger;
7 | logger.makeLogger = function (loaderOptions, colors) {
8 | const instance = makeLogger(loaderOptions, colors);
9 | const logWarning = instance.logWarning;
10 | instance.logWarning = function (message) {
11 | // Disable TS Loader TypeScript compatibility warning
12 | if (message.indexOf('This version may or may not be compatible with ts-loader') !== -1)
13 | return;
14 | return logWarning(message);
15 | };
16 | return instance;
17 | };
18 |
19 | module.exports = require("ts-loader");
20 |
21 | // ts-loader internally has a require("typescript") that applies
22 | // regardless of "compiler".
23 | // We could remap this too, as soon as ncc supports aliased externals
24 | module.exports.typescript = require("typescript");
25 |
--------------------------------------------------------------------------------
/src/loaders/uncacheable.js:
--------------------------------------------------------------------------------
1 | module.exports = function (input, map) {
2 | this.cacheable(false);
3 | return this.callback(null, input, map);
4 | };
--------------------------------------------------------------------------------
/src/sourcemap-register.js.cache.js:
--------------------------------------------------------------------------------
1 | ../dist/ncc/sourcemap-register.js.cache.js
--------------------------------------------------------------------------------
/src/typescript.js:
--------------------------------------------------------------------------------
1 |
2 | const { Module } = require('module');
3 | const m = new Module('', null);
4 | const { quiet, typescriptLookupPath } = JSON.parse(process.env.__NCC_OPTS || '{}');
5 | m.paths = Module._nodeModulePaths(process.env.TYPESCRIPT_LOOKUP_PATH || typescriptLookupPath || (process.cwd() + '/'));
6 | let typescript;
7 | try {
8 | typescript = m.require('typescript');
9 | if (!quiet) console.log("ncc: Using typescript@" + typescript.version + " (local user-provided)");
10 | }
11 | catch (e) {
12 | typescript = require('typescript');
13 | if (!quiet) console.log("ncc: Using typescript@" + typescript.version + " (ncc built-in)");
14 | }
15 | module.exports = typescript;
16 |
--------------------------------------------------------------------------------
/src/utils/get-package-base.js:
--------------------------------------------------------------------------------
1 | // returns the base-level package folder based on detecting "node_modules"
2 | // package name boundaries
3 | const pkgNameRegEx = /^(@[^\\\/]+[\\\/])?[^\\\/]+/;
4 | module.exports = function (id) {
5 | const pkgIndex = id.lastIndexOf('node_modules');
6 | if (pkgIndex !== -1 &&
7 | (id[pkgIndex - 1] === '/' || id[pkgIndex - 1] === '\\') &&
8 | (id[pkgIndex + 12] === '/' || id[pkgIndex + 12] === '\\')) {
9 | const pkgNameMatch = id.substr(pkgIndex + 13).match(pkgNameRegEx);
10 | if (pkgNameMatch)
11 | return id.substr(0, pkgIndex + 13 + pkgNameMatch[0].length);
12 | }
13 | };
14 |
15 | module.exports.pkgNameRegEx = pkgNameRegEx;
--------------------------------------------------------------------------------
/src/utils/has-type-module.js:
--------------------------------------------------------------------------------
1 | const { resolve } = require('path');
2 | const { readFileSync } = require('fs');
3 |
4 | exports.hasTypeModule = function hasTypeModule (path) {
5 | while (path !== (path = resolve(path, '..'))) {
6 | try {
7 | return JSON.parse(readFileSync(eval('resolve')(path, 'package.json')).toString()).type === 'module';
8 | }
9 | catch (e) {
10 | if (e.code === 'ENOENT')
11 | continue;
12 | throw e;
13 | }
14 | }
15 | }
16 |
--------------------------------------------------------------------------------
/src/utils/ncc-cache-dir.js:
--------------------------------------------------------------------------------
1 | module.exports = require("os").tmpdir() + "/ncc-cache";
--------------------------------------------------------------------------------
/src/utils/shebang.js:
--------------------------------------------------------------------------------
1 | module.exports = /^#![^\n\r]*[\r\n]/;
--------------------------------------------------------------------------------
/test/binary/binding.gyp:
--------------------------------------------------------------------------------
1 | {
2 | "targets": [
3 | {
4 | "target_name": "hello",
5 | "sources": [ "hello.cc" ],
6 | "include_dirs": [
7 | "
3 |
4 | namespace demo {
5 |
6 | using v8::FunctionCallbackInfo;
7 | using v8::Isolate;
8 | using v8::Local;
9 | using v8::NewStringType;
10 | using v8::Object;
11 | using v8::String;
12 | using v8::Value;
13 |
14 | void Method(const FunctionCallbackInfo& args) {
15 | Isolate* isolate = args.GetIsolate();
16 | args.GetReturnValue().Set(String::NewFromUtf8(
17 | isolate, "world", NewStringType::kNormal).ToLocalChecked());
18 | }
19 |
20 | void Initialize(Local