拿掉 build files

This commit is contained in:
2022-07-18 16:33:23 +08:00
parent 41e2287bcb
commit 3707f158a3
31953 changed files with 0 additions and 4411796 deletions
-21
View File
@@ -1,21 +0,0 @@
The MIT License (MIT)
Copyright (c) 2014 Blake Embrey (hello@blakeembrey.com)
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:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
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.
-302
View File
@@ -1,302 +0,0 @@
# ![TypeScript Node](logo.svg?sanitize=true)
[![NPM version][npm-image]][npm-url]
[![NPM downloads][downloads-image]][downloads-url]
[![Build status][travis-image]][travis-url]
[![Test coverage][coveralls-image]][coveralls-url]
> TypeScript execution and REPL for node.js, with source map support. **Works with `typescript@>=2.7`**.
### *Experimental ESM support*
Native ESM support is currently experimental. For usage, limitations, and to provide feedback, see [#1007](https://github.com/TypeStrong/ts-node/issues/1007).
## Installation
```sh
# Locally in your project.
npm install -D typescript
npm install -D ts-node
# Or globally with TypeScript.
npm install -g typescript
npm install -g ts-node
```
**Tip:** Installing modules locally allows you to control and share the versions through `package.json`. TS Node will always resolve the compiler from `cwd` before checking relative to its own installation.
## Usage
### Shell
```sh
# Execute a script as `node` + `tsc`.
ts-node script.ts
# Starts a TypeScript REPL.
ts-node
# Execute code with TypeScript.
ts-node -e 'console.log("Hello, world!")'
# Execute, and print, code with TypeScript.
ts-node -p -e '"Hello, world!"'
# Pipe scripts to execute with TypeScript.
echo 'console.log("Hello, world!")' | ts-node
# Equivalent to ts-node --script-mode
ts-node-script scripts.ts
# Equivalent to ts-node --transpile-only
ts-node-transpile-only scripts.ts
```
![TypeScript REPL](https://github.com/TypeStrong/ts-node/raw/master/screenshot.png)
### Shebang
```typescript
#!/usr/bin/env ts-node-script
console.log("Hello, world!")
```
`ts-node-script` is recommended because it enables `--script-mode`, discovering `tsconfig.json` relative to the script's location instead of `process.cwd()`. This makes scripts more portable.
Passing CLI arguments via shebang is allowed on Mac but not Linux. For example, the following will fail on Linux:
```
#!/usr/bin/env ts-node --script-mode --transpile-only --files
// This shebang is not portable. It only works on Mac
```
### Programmatic
You can require `ts-node` and register the loader for future requires by using `require('ts-node').register({ /* options */ })`. You can also use file shortcuts - `node -r ts-node/register` or `node -r ts-node/register/transpile-only` - depending on your preferences.
**Note:** If you need to use advanced node.js CLI arguments (e.g. `--inspect`), use them with `node -r ts-node/register` instead of the `ts-node` CLI.
#### Developers
**TS Node** exports a `create()` function that can be used to initialize a TypeScript compiler that isn't registered to `require.extensions`, and it uses the same code as `register`.
### Mocha
Mocha 6
```sh
mocha --require ts-node/register --watch-extensions ts,tsx "test/**/*.{ts,tsx}" [...args]
```
**Note:** `--watch-extensions` is only used in `--watch` mode.
Mocha 7
```sh
mocha --require ts-node/register --extensions ts,tsx --watch --watch-files src 'tests/**/*.{ts,tsx}' [...args]
```
### Tape
```sh
ts-node node_modules/tape/bin/tape [...args]
```
### Gulp
```sh
# Create a `gulpfile.ts` and run `gulp`.
gulp
```
### Visual Studio Code
Create a new node.js configuration, add `-r ts-node/register` to node args and move the `program` to the `args` list (so VS Code doesn't look for `outFiles`).
```json
{
"type": "node",
"request": "launch",
"name": "Launch Program",
"runtimeArgs": [
"-r",
"ts-node/register"
],
"args": [
"${workspaceFolder}/index.ts"
]
}
```
**Note:** If you are using the `--project <tsconfig.json>` command line argument as per the [Configuration Options](#configuration-options), and want to apply this same behavior when launching in VS Code, add an "env" key into the launch configuration: `"env": { "TS_NODE_PROJECT": "<tsconfig.json>" }`.
### IntelliJ (and WebStorm)
Create a new Node.js configuration and add `-r ts-node/register` to "Node parameters."
**Note:** If you are using the `--project <tsconfig.json>` command line argument as per the [Configuration Options](#configuration-options), and want to apply this same behavior when launching in IntelliJ, specify under "Environment Variables": `TS_NODE_PROJECT=<tsconfig.json>`.
## How It Works
**TypeScript Node** works by registering the TypeScript compiler for `.tsx?` and `.jsx?` (when `allowJs == true`) extensions. When node.js has an extension registered (via `require.extensions`), it will use the extension internally for module resolution. When an extension is unknown to node.js, it handles the file as `.js` (JavaScript). By default, **TypeScript Node** avoids compiling files in `/node_modules/` for three reasons:
1. Modules should always be published in a format node.js can consume
2. Transpiling the entire dependency tree will make your project slower
3. Differing behaviours between TypeScript and node.js (e.g. ES2015 modules) can result in a project that works until you decide to support a feature natively from node.js
**P.S.** This means if you don't register an extension, it is compiled as JavaScript. When `ts-node` is used with `allowJs`, JavaScript files are transpiled using the TypeScript compiler.
## Loading `tsconfig.json`
**Typescript Node** loads `tsconfig.json` automatically. Use `--skip-project` to skip loading the `tsconfig.json`.
It is resolved relative to `--dir` using [the same search behavior as `tsc`](https://www.typescriptlang.org/docs/handbook/tsconfig-json.html). In `--script-mode`, this is the directory containing the script. Otherwise it is resolved relative to `process.cwd()`, which matches the behavior of `tsc`.
Use `--project` to specify the path to your `tsconfig.json`, ignoring `--dir`.
**Tip**: You can use `ts-node` together with [tsconfig-paths](https://www.npmjs.com/package/tsconfig-paths) to load modules according to the `paths` section in `tsconfig.json`.
## Configuration Options
You can set options by passing them before the script path, via programmatic usage, via `tsconfig.json`, or via environment variables.
```sh
ts-node --compiler ntypescript --project src/tsconfig.json hello-world.ts
```
**Note:** [`ntypescript`](https://github.com/TypeStrong/ntypescript#readme) is an example of a TypeScript-compatible `compiler`.
### CLI Options
`ts-node` supports `--print` (`-p`), `--eval` (`-e`), `--require` (`-r`) and `--interactive` (`-i`) similar to the [node.js CLI options](https://nodejs.org/api/cli.html).
* `-h, --help` Prints the help text
* `-v, --version` Prints the version. `-vv` prints node and typescript compiler versions, too
* `-s, --script-mode` Resolve config relative to the directory of the passed script instead of the current directory. Changes default of `--dir`
### CLI and Programmatic Options
_The name of the environment variable and the option's default value are denoted in parentheses._
* `-T, --transpile-only` Use TypeScript's faster `transpileModule` (`TS_NODE_TRANSPILE_ONLY`, default: `false`)
* `-H, --compiler-host` Use TypeScript's compiler host API (`TS_NODE_COMPILER_HOST`, default: `false`)
* `-I, --ignore [pattern]` Override the path patterns to skip compilation (`TS_NODE_IGNORE`, default: `/node_modules/`)
* `-P, --project [path]` Path to TypeScript JSON project file (`TS_NODE_PROJECT`)
* `-C, --compiler [name]` Specify a custom TypeScript compiler (`TS_NODE_COMPILER`, default: `typescript`)
* `-D, --ignore-diagnostics [code]` Ignore TypeScript warnings by diagnostic code (`TS_NODE_IGNORE_DIAGNOSTICS`)
* `-O, --compiler-options [opts]` JSON object to merge with compiler options (`TS_NODE_COMPILER_OPTIONS`)
* `--dir` Specify working directory for config resolution (`TS_NODE_CWD`, default: `process.cwd()`, or `dirname(scriptPath)` if `--script-mode`)
* `--scope` Scope compiler to files within `cwd` (`TS_NODE_SCOPE`, default: `false`)
* `--files` Load `files`, `include` and `exclude` from `tsconfig.json` on startup (`TS_NODE_FILES`, default: `false`)
* `--pretty` Use pretty diagnostic formatter (`TS_NODE_PRETTY`, default: `false`)
* `--skip-project` Skip project config resolution and loading (`TS_NODE_SKIP_PROJECT`, default: `false`)
* `--skip-ignore` Skip ignore checks (`TS_NODE_SKIP_IGNORE`, default: `false`)
* `--emit` Emit output files into `.ts-node` directory (`TS_NODE_EMIT`, default: `false`)
* `--prefer-ts-exts` Re-order file extensions so that TypeScript imports are preferred (`TS_NODE_PREFER_TS_EXTS`, default: `false`)
* `--log-error` Logs TypeScript errors to stderr instead of throwing exceptions (`TS_NODE_LOG_ERROR`, default: `false`)
### Programmatic-only Options
* `transformers` `_ts.CustomTransformers | ((p: _ts.Program) => _ts.CustomTransformers)`: An object with transformers or a function that accepts a program and returns an transformers object to pass to TypeScript. Function isn't available with `transpileOnly` flag
* `readFile`: Custom TypeScript-compatible file reading function
* `fileExists`: Custom TypeScript-compatible file existence function
### Options via tsconfig.json
Most options can be specified by a `"ts-node"` object in `tsconfig.json` using their programmatic, camelCase names. For example, to enable `--transpile-only`:
```json
// tsconfig.json
{
"ts-node": {
"transpileOnly": true
},
"compilerOptions": {}
}
```
Our bundled [JSON schema](https://unpkg.com/browse/ts-node@8.8.2/tsconfig.schema.json) lists all compatible options.
## SyntaxError
Any error that is not a `TSError` is from node.js (e.g. `SyntaxError`), and cannot be fixed by TypeScript or `ts-node`. These are runtime issues with your code.
### Import Statements
Current node.js stable releases do not support ES modules. Additionally, `ts-node` does not have the required hooks into node.js to support ES modules. You will need to set `"module": "commonjs"` in your `tsconfig.json` for your code to work.
## Help! My Types Are Missing!
**TypeScript Node** does _not_ use `files`, `include` or `exclude`, by default. This is because a large majority projects do not use all of the files in a project directory (e.g. `Gulpfile.ts`, runtime vs tests) and parsing every file for types slows startup time. Instead, `ts-node` starts with the script file (e.g. `ts-node index.ts`) and TypeScript resolves dependencies based on imports and references.
For global definitions, you can use the `typeRoots` compiler option. This requires that your type definitions be structured as type packages (not loose TypeScript definition files). More details on how this works can be found in the [TypeScript Handbook](https://www.typescriptlang.org/docs/handbook/tsconfig-json.html#types-typeroots-and-types).
Example `tsconfig.json`:
```json
{
"compilerOptions": {
"typeRoots" : ["./node_modules/@types", "./typings"]
}
}
```
Example project structure:
```text
<project_root>/
-- tsconfig.json
-- typings/
-- <module_name>/
-- index.d.ts
```
Example module declaration file:
```typescript
declare module '<module_name>' {
// module definitions go here
}
```
For module definitions, you can use [`paths`](https://www.typescriptlang.org/docs/handbook/module-resolution.html#path-mapping):
```json
{
"compilerOptions": {
"baseUrl": ".",
"paths": {
"custom-module-type": ["types/custom-module-type"]
}
}
}
```
An alternative approach for definitions of third-party libraries are [triple-slash directives](https://www.typescriptlang.org/docs/handbook/triple-slash-directives.html). This may be helpful if you prefer not to change your TypeScript `compilerOptions` or structure your custom type definitions when using `typeRoots`. Below is an example of the triple-slash directive as a relative path within your project:
```typescript
/// <reference types="./types/untyped_js_lib" />
import UntypedJsLib from "untyped_js_lib"
```
**Tip:** If you _must_ use `files`, `include`, or `exclude`, enable `--files` flags or set `TS_NODE_FILES=true`.
## Watching and Restarting
**TypeScript Node** compiles source code via `require()`, watching files and code reloads are out of scope for the project. If you want to restart the `ts-node` process on file change, existing node.js tools such as [nodemon](https://github.com/remy/nodemon), [onchange](https://github.com/Qard/onchange) and [node-dev](https://github.com/fgnass/node-dev) work.
There's also [`ts-node-dev`](https://github.com/whitecolor/ts-node-dev), a modified version of [`node-dev`](https://github.com/fgnass/node-dev) using `ts-node` for compilation and won't restart the process on file change.
## License
MIT
[npm-image]: https://img.shields.io/npm/v/ts-node.svg?style=flat
[npm-url]: https://npmjs.org/package/ts-node
[downloads-image]: https://img.shields.io/npm/dm/ts-node.svg?style=flat
[downloads-url]: https://npmjs.org/package/ts-node
[travis-image]: https://img.shields.io/travis/TypeStrong/ts-node.svg?style=flat
[travis-url]: https://travis-ci.org/TypeStrong/ts-node
[coveralls-image]: https://img.shields.io/coveralls/TypeStrong/ts-node.svg?style=flat
[coveralls-url]: https://coveralls.io/r/TypeStrong/ts-node?branch=master
-772
View File
@@ -1,772 +0,0 @@
// Copied from https://raw.githubusercontent.com/nodejs/node/v13.12.0/lib/internal/modules/esm/resolve.js
// Then modified to suite our needs.
// Formatting is intentionally bad to keep the diff as small as possible, to make it easier to merge
// upstream changes and understand our modifications.
'use strict';
const {
ArrayIsArray,
JSONParse,
JSONStringify,
ObjectGetOwnPropertyNames,
ObjectPrototypeHasOwnProperty,
SafeMap,
StringPrototypeEndsWith,
StringPrototypeIncludes,
StringPrototypeIndexOf,
StringPrototypeSlice,
StringPrototypeStartsWith,
StringPrototypeSubstr,
} = {
ArrayIsArray: Array.isArray,
JSONParse: JSON.parse,
JSONStringify: JSON.stringify,
ObjectGetOwnPropertyNames: Object.getOwnPropertyNames,
ObjectPrototypeHasOwnProperty: (obj, prop) => Object.prototype.hasOwnProperty.call(obj, prop),
SafeMap: Map,
StringPrototypeEndsWith: (str, ...rest) => String.prototype.endsWith.apply(str, rest),
StringPrototypeIncludes: (str, ...rest) => String.prototype.includes.apply(str, rest),
StringPrototypeIndexOf: (str, ...rest) => String.prototype.indexOf.apply(str, rest),
StringPrototypeSlice: (str, ...rest) => String.prototype.slice.apply(str, rest),
StringPrototypeStartsWith: (str, ...rest) => String.prototype.startsWith.apply(str, rest),
StringPrototypeSubstr: (str, ...rest) => String.prototype.substr.apply(str, rest),
} // node pulls from `primordials` object
// const internalFS = require('internal/fs/utils');
// const { NativeModule } = require('internal/bootstrap/loaders');
const Module = require('module')
const NativeModule = {
canBeRequiredByUsers(specifier) {
return Module.builtinModules.includes(specifier)
}
}
const {
closeSync,
fstatSync,
openSync,
readFileSync,
realpathSync,
statSync,
Stats,
} = require('fs');
// const { getOptionValue } = require('internal/options');
const { getOptionValue } = (() => {
let options;
function parseOptions() {
if (!options) {
options = {
'--preserve-symlinks': false,
'--preserve-symlinks-main': false,
'--input-type': undefined,
'--experimental-specifier-resolution': 'explicit',
...parseExecArgv()
}
}
};
function parseExecArgv () {
return require('arg')({
'--preserve-symlinks': Boolean,
'--preserve-symlinks-main': Boolean,
'--input-type': String,
'--experimental-specifier-resolution': String
}, {
argv: process.execArgv,
permissive: true
});
}
return {
getOptionValue: (opt) => {
parseOptions();
return options[opt];
}
};
})();
const { sep } = require('path');
const preserveSymlinks = getOptionValue('--preserve-symlinks');
const preserveSymlinksMain = getOptionValue('--preserve-symlinks-main');
const typeFlag = getOptionValue('--input-type');
// const { URL, pathToFileURL, fileURLToPath } = require('internal/url');
const { URL, pathToFileURL, fileURLToPath } = require('url');
const {
ERR_INPUT_TYPE_NOT_ALLOWED,
ERR_INVALID_MODULE_SPECIFIER,
ERR_INVALID_PACKAGE_CONFIG,
ERR_INVALID_PACKAGE_TARGET,
ERR_MODULE_NOT_FOUND,
ERR_PACKAGE_PATH_NOT_EXPORTED,
ERR_UNSUPPORTED_ESM_URL_SCHEME,
// } = require('internal/errors').codes;
} = {
ERR_INPUT_TYPE_NOT_ALLOWED: createErrorCtor('ERR_INPUT_TYPE_NOT_ALLOWED'),
ERR_INVALID_MODULE_SPECIFIER: createErrorCtor('ERR_INVALID_MODULE_SPECIFIER'),
ERR_INVALID_PACKAGE_CONFIG: createErrorCtor('ERR_INVALID_PACKAGE_CONFIG'),
ERR_INVALID_PACKAGE_TARGET: createErrorCtor('ERR_INVALID_PACKAGE_TARGET'),
ERR_MODULE_NOT_FOUND: createErrorCtor('ERR_MODULE_NOT_FOUND'),
ERR_PACKAGE_PATH_NOT_EXPORTED: createErrorCtor('ERR_PACKAGE_PATH_NOT_EXPORTED'),
ERR_UNSUPPORTED_ESM_URL_SCHEME: createErrorCtor('ERR_UNSUPPORTED_ESM_URL_SCHEME'),
}
function createErrorCtor(name) {
return class CustomError extends Error {
constructor(...args) {
super([name, ...args].join(' '))
}
}
}
function createResolve(opts) {
// TODO receive cached fs implementations here
const {tsExtensions, jsExtensions, preferTsExts} = opts;
const realpathCache = new SafeMap();
const packageJSONCache = new SafeMap(); /* string -> PackageConfig */
function tryStatSync(path) {
try {
return statSync(path);
} catch {
return new Stats();
}
}
function readIfFile(path) {
let fd;
try {
fd = openSync(path, 'r');
} catch {
return undefined;
}
try {
if (!fstatSync(fd).isFile()) return undefined;
return readFileSync(fd, 'utf8');
} finally {
closeSync(fd);
}
}
function getPackageConfig(path, base) {
const existing = packageJSONCache.get(path);
if (existing !== undefined) {
if (!existing.isValid) {
throw new ERR_INVALID_PACKAGE_CONFIG(path, fileURLToPath(base), false);
}
return existing;
}
const source = readIfFile(path);
if (source === undefined) {
const packageConfig = {
exists: false,
main: undefined,
name: undefined,
isValid: true,
type: 'none',
exports: undefined
};
packageJSONCache.set(path, packageConfig);
return packageConfig;
}
let packageJSON;
try {
packageJSON = JSONParse(source);
} catch {
const packageConfig = {
exists: true,
main: undefined,
name: undefined,
isValid: false,
type: 'none',
exports: undefined
};
packageJSONCache.set(path, packageConfig);
return packageConfig;
}
let { main, name, type } = packageJSON;
const { exports } = packageJSON;
if (typeof main !== 'string') main = undefined;
if (typeof name !== 'string') name = undefined;
// Ignore unknown types for forwards compatibility
if (type !== 'module' && type !== 'commonjs') type = 'none';
const packageConfig = {
exists: true,
main,
name,
isValid: true,
type,
exports
};
packageJSONCache.set(path, packageConfig);
return packageConfig;
}
function getPackageScopeConfig(resolved, base) {
let packageJSONUrl = new URL('./package.json', resolved);
while (true) {
const packageJSONPath = packageJSONUrl.pathname;
if (StringPrototypeEndsWith(packageJSONPath, 'node_modules/package.json'))
break;
const packageConfig = getPackageConfig(fileURLToPath(packageJSONUrl), base);
if (packageConfig.exists) return packageConfig;
const lastPackageJSONUrl = packageJSONUrl;
packageJSONUrl = new URL('../package.json', packageJSONUrl);
// Terminates at root where ../package.json equals ../../package.json
// (can't just check "/package.json" for Windows support).
if (packageJSONUrl.pathname === lastPackageJSONUrl.pathname) break;
}
const packageConfig = {
exists: false,
main: undefined,
name: undefined,
isValid: true,
type: 'none',
exports: undefined
};
packageJSONCache.set(fileURLToPath(packageJSONUrl), packageConfig);
return packageConfig;
}
/*
* Legacy CommonJS main resolution:
* 1. let M = pkg_url + (json main field)
* 2. TRY(M, M.js, M.json, M.node)
* 3. TRY(M/index.js, M/index.json, M/index.node)
* 4. TRY(pkg_url/index.js, pkg_url/index.json, pkg_url/index.node)
* 5. NOT_FOUND
*/
function fileExists(url) {
return tryStatSync(fileURLToPath(url)).isFile();
}
function legacyMainResolve(packageJSONUrl, packageConfig) {
let guess;
if (packageConfig.main !== undefined) {
// Note: fs check redundances will be handled by Descriptor cache here.
if (fileExists(guess = new URL(`./${packageConfig.main}`,
packageJSONUrl))) {
return guess;
}
if (fileExists(guess = new URL(`./${packageConfig.main}.js`,
packageJSONUrl))) {
return guess;
}
if (fileExists(guess = new URL(`./${packageConfig.main}.json`,
packageJSONUrl))) {
return guess;
}
if (fileExists(guess = new URL(`./${packageConfig.main}.node`,
packageJSONUrl))) {
return guess;
}
if (fileExists(guess = new URL(`./${packageConfig.main}/index.js`,
packageJSONUrl))) {
return guess;
}
if (fileExists(guess = new URL(`./${packageConfig.main}/index.json`,
packageJSONUrl))) {
return guess;
}
if (fileExists(guess = new URL(`./${packageConfig.main}/index.node`,
packageJSONUrl))) {
return guess;
}
// Fallthrough.
}
if (fileExists(guess = new URL('./index.js', packageJSONUrl))) {
return guess;
}
// So fs.
if (fileExists(guess = new URL('./index.json', packageJSONUrl))) {
return guess;
}
if (fileExists(guess = new URL('./index.node', packageJSONUrl))) {
return guess;
}
// Not found.
return undefined;
}
function resolveExtensionsWithTryExactName(search) {
if (fileExists(search)) return search;
const resolvedReplacementExtension = resolveReplacementExtensions(search);
if(resolvedReplacementExtension) return resolvedReplacementExtension;
return resolveExtensions(search);
}
const extensions = Array.from(new Set([
...(preferTsExts ? tsExtensions : []),
'.js',
...jsExtensions,
'.json', '.node', '.mjs',
...tsExtensions
]));
function resolveExtensions(search) {
for (let i = 0; i < extensions.length; i++) {
const extension = extensions[i];
const guess = new URL(`${search.pathname}${extension}`, search);
if (fileExists(guess)) return guess;
}
return undefined;
}
/**
* TS's resolver can resolve foo.js to foo.ts, by replacing .js extension with several source extensions.
* IMPORTANT: preserve ordering according to preferTsExts; this affects resolution behavior!
*/
const replacementExtensions = extensions.filter(ext => ['.js', '.jsx', '.ts', '.tsx'].includes(ext));
function resolveReplacementExtensions(search) {
if (search.pathname.match(/\.js$/)) {
const pathnameWithoutExtension = search.pathname.slice(0, search.pathname.length - 3);
for (let i = 0; i < replacementExtensions.length; i++) {
const extension = replacementExtensions[i];
const guess = new URL(`${pathnameWithoutExtension}${extension}`, search);
if (fileExists(guess)) return guess;
}
}
return undefined;
}
function resolveIndex(search) {
return resolveExtensions(new URL('index', search));
}
function finalizeResolution(resolved, base) {
if (getOptionValue('--experimental-specifier-resolution') === 'node') {
let file = resolveExtensionsWithTryExactName(resolved);
if (file !== undefined) return file;
if (!StringPrototypeEndsWith(resolved.pathname, '/')) {
file = resolveIndex(new URL(`${resolved.pathname}/`, base));
} else {
file = resolveIndex(resolved);
}
if (file !== undefined) return file;
throw new ERR_MODULE_NOT_FOUND(
resolved.pathname, fileURLToPath(base), 'module');
}
if (StringPrototypeEndsWith(resolved.pathname, '/')) return resolved;
const file = resolveReplacementExtensions(resolved) || resolved;
const path = fileURLToPath(file);
if (!tryStatSync(path).isFile()) {
throw new ERR_MODULE_NOT_FOUND(
path || resolved.pathname, fileURLToPath(base), 'module');
}
return file;
}
function throwExportsNotFound(subpath, packageJSONUrl, base) {
throw new ERR_PACKAGE_PATH_NOT_EXPORTED(
fileURLToPath(packageJSONUrl), subpath, fileURLToPath(base));
}
function throwSubpathInvalid(subpath, packageJSONUrl, base) {
throw new ERR_INVALID_MODULE_SPECIFIER(
fileURLToPath(packageJSONUrl), subpath, fileURLToPath(base));
}
function throwExportsInvalid(
subpath, target, packageJSONUrl, base) {
if (typeof target === 'object' && target !== null) {
target = JSONStringify(target, null, '');
} else if (ArrayIsArray(target)) {
target = `[${target}]`;
} else {
target = `${target}`;
}
throw new ERR_INVALID_PACKAGE_TARGET(
fileURLToPath(packageJSONUrl), null, subpath, target, fileURLToPath(base));
}
function resolveExportsTargetString(
target, subpath, match, packageJSONUrl, base) {
if (target[0] !== '.' || target[1] !== '/' ||
(subpath !== '' && target[target.length - 1] !== '/')) {
throwExportsInvalid(match, target, packageJSONUrl, base);
}
const resolved = new URL(target, packageJSONUrl);
const resolvedPath = resolved.pathname;
const packagePath = new URL('.', packageJSONUrl).pathname;
if (!StringPrototypeStartsWith(resolvedPath, packagePath) ||
StringPrototypeIncludes(
resolvedPath, '/node_modules/', packagePath.length - 1)) {
throwExportsInvalid(match, target, packageJSONUrl, base);
}
if (subpath === '') return resolved;
const subpathResolved = new URL(subpath, resolved);
const subpathResolvedPath = subpathResolved.pathname;
if (!StringPrototypeStartsWith(subpathResolvedPath, resolvedPath) ||
StringPrototypeIncludes(subpathResolvedPath,
'/node_modules/', packagePath.length - 1)) {
throwSubpathInvalid(match + subpath, packageJSONUrl, base);
}
return subpathResolved;
}
function isArrayIndex(key /* string */) { /* -> boolean */
const keyNum = +key;
if (`${keyNum}` !== key) return false;
return keyNum >= 0 && keyNum < 0xFFFF_FFFF;
}
function resolveExportsTarget(
packageJSONUrl, target, subpath, packageSubpath, base) {
if (typeof target === 'string') {
const resolved = resolveExportsTargetString(
target, subpath, packageSubpath, packageJSONUrl, base);
return finalizeResolution(resolved, base);
} else if (ArrayIsArray(target)) {
if (target.length === 0)
throwExportsInvalid(packageSubpath, target, packageJSONUrl, base);
let lastException;
for (let i = 0; i < target.length; i++) {
const targetItem = target[i];
let resolved;
try {
resolved = resolveExportsTarget(
packageJSONUrl, targetItem, subpath, packageSubpath, base);
} catch (e) {
lastException = e;
if (e.code === 'ERR_PACKAGE_PATH_NOT_EXPORTED' ||
e.code === 'ERR_INVALID_PACKAGE_TARGET') {
continue;
}
throw e;
}
return finalizeResolution(resolved, base);
}
throw lastException;
} else if (typeof target === 'object' && target !== null) {
const keys = ObjectGetOwnPropertyNames(target);
for (let i = 0; i < keys.length; i++) {
const key = keys[i];
if (isArrayIndex(key)) {
throw new ERR_INVALID_PACKAGE_CONFIG(
fileURLToPath(packageJSONUrl),
'"exports" cannot contain numeric property keys');
}
}
for (let i = 0; i < keys.length; i++) {
const key = keys[i];
if (key === 'node' || key === 'import' || key === 'default') {
const conditionalTarget = target[key];
try {
return resolveExportsTarget(
packageJSONUrl, conditionalTarget, subpath, packageSubpath, base);
} catch (e) {
if (e.code === 'ERR_PACKAGE_PATH_NOT_EXPORTED') continue;
throw e;
}
}
}
throwExportsNotFound(packageSubpath, packageJSONUrl, base);
}
throwExportsInvalid(packageSubpath, target, packageJSONUrl, base);
}
function isConditionalExportsMainSugar(exports, packageJSONUrl, base) {
if (typeof exports === 'string' || ArrayIsArray(exports)) return true;
if (typeof exports !== 'object' || exports === null) return false;
const keys = ObjectGetOwnPropertyNames(exports);
let isConditionalSugar = false;
let i = 0;
for (let j = 0; j < keys.length; j++) {
const key = keys[j];
const curIsConditionalSugar = key === '' || key[0] !== '.';
if (i++ === 0) {
isConditionalSugar = curIsConditionalSugar;
} else if (isConditionalSugar !== curIsConditionalSugar) {
throw new ERR_INVALID_PACKAGE_CONFIG(
fileURLToPath(packageJSONUrl),
'"exports" cannot contain some keys starting with \'.\' and some not.' +
' The exports object must either be an object of package subpath keys' +
' or an object of main entry condition name keys only.');
}
}
return isConditionalSugar;
}
function packageMainResolve(packageJSONUrl, packageConfig, base) {
if (packageConfig.exists) {
const exports = packageConfig.exports;
if (exports !== undefined) {
if (isConditionalExportsMainSugar(exports, packageJSONUrl, base)) {
return resolveExportsTarget(packageJSONUrl, exports, '', '', base);
} else if (typeof exports === 'object' && exports !== null) {
const target = exports['.'];
if (target !== undefined)
return resolveExportsTarget(packageJSONUrl, target, '', '', base);
}
throw new ERR_PACKAGE_PATH_NOT_EXPORTED(packageJSONUrl, '.');
}
if (packageConfig.main !== undefined) {
const resolved = new URL(packageConfig.main, packageJSONUrl);
const path = fileURLToPath(resolved);
if (tryStatSync(path).isFile()) return resolved;
}
if (getOptionValue('--experimental-specifier-resolution') === 'node') {
if (packageConfig.main !== undefined) {
return finalizeResolution(
new URL(packageConfig.main, packageJSONUrl), base);
} else {
return finalizeResolution(
new URL('index', packageJSONUrl), base);
}
}
if (packageConfig.type !== 'module') {
return legacyMainResolve(packageJSONUrl, packageConfig);
}
}
throw new ERR_MODULE_NOT_FOUND(
fileURLToPath(new URL('.', packageJSONUrl)), fileURLToPath(base));
}
function packageExportsResolve(
packageJSONUrl, packageSubpath, packageConfig, base) /* -> URL */ {
const exports = packageConfig.exports;
if (exports === undefined ||
isConditionalExportsMainSugar(exports, packageJSONUrl, base)) {
throwExportsNotFound(packageSubpath, packageJSONUrl, base);
}
if (ObjectPrototypeHasOwnProperty(exports, packageSubpath)) {
const target = exports[packageSubpath];
const resolved = resolveExportsTarget(
packageJSONUrl, target, '', packageSubpath, base);
return finalizeResolution(resolved, base);
}
let bestMatch = '';
const keys = ObjectGetOwnPropertyNames(exports);
for (let i = 0; i < keys.length; i++) {
const key = keys[i];
if (key[key.length - 1] !== '/') continue;
if (StringPrototypeStartsWith(packageSubpath, key) &&
key.length > bestMatch.length) {
bestMatch = key;
}
}
if (bestMatch) {
const target = exports[bestMatch];
const subpath = StringPrototypeSubstr(packageSubpath, bestMatch.length);
const resolved = resolveExportsTarget(
packageJSONUrl, target, subpath, packageSubpath, base);
return finalizeResolution(resolved, base);
}
throwExportsNotFound(packageSubpath, packageJSONUrl, base);
}
function getPackageType(url) {
const packageConfig = getPackageScopeConfig(url, url);
return packageConfig.type;
}
function packageResolve(specifier /* string */, base /* URL */) { /* -> URL */
let separatorIndex = StringPrototypeIndexOf(specifier, '/');
let validPackageName = true;
let isScoped = false;
if (specifier[0] === '@') {
isScoped = true;
if (separatorIndex === -1 || specifier.length === 0) {
validPackageName = false;
} else {
separatorIndex = StringPrototypeIndexOf(
specifier, '/', separatorIndex + 1);
}
}
const packageName = separatorIndex === -1 ?
specifier : StringPrototypeSlice(specifier, 0, separatorIndex);
// Package name cannot have leading . and cannot have percent-encoding or
// separators.
for (let i = 0; i < packageName.length; i++) {
if (packageName[i] === '%' || packageName[i] === '\\') {
validPackageName = false;
break;
}
}
if (!validPackageName) {
throw new ERR_INVALID_MODULE_SPECIFIER(
specifier, undefined, fileURLToPath(base));
}
const packageSubpath = separatorIndex === -1 ?
'' : '.' + StringPrototypeSlice(specifier, separatorIndex);
// ResolveSelf
const packageConfig = getPackageScopeConfig(base, base);
if (packageConfig.exists) {
// TODO(jkrems): Find a way to forward the pair/iterator already generated
// while executing GetPackageScopeConfig
let packageJSONUrl;
for (const [ filename, packageConfigCandidate ] of packageJSONCache) {
if (packageConfig === packageConfigCandidate) {
packageJSONUrl = pathToFileURL(filename);
break;
}
}
if (packageJSONUrl !== undefined &&
packageConfig.name === packageName &&
packageConfig.exports !== undefined) {
if (packageSubpath === './') {
return new URL('./', packageJSONUrl);
} else if (packageSubpath === '') {
return packageMainResolve(packageJSONUrl, packageConfig, base);
} else {
return packageExportsResolve(
packageJSONUrl, packageSubpath, packageConfig, base);
}
}
}
let packageJSONUrl =
new URL('./node_modules/' + packageName + '/package.json', base);
let packageJSONPath = fileURLToPath(packageJSONUrl);
let lastPath;
do {
const stat = tryStatSync(
StringPrototypeSlice(packageJSONPath, 0, packageJSONPath.length - 13));
if (!stat.isDirectory()) {
lastPath = packageJSONPath;
packageJSONUrl = new URL((isScoped ?
'../../../../node_modules/' : '../../../node_modules/') +
packageName + '/package.json', packageJSONUrl);
packageJSONPath = fileURLToPath(packageJSONUrl);
continue;
}
// Package match.
const packageConfig = getPackageConfig(packageJSONPath, base);
if (packageSubpath === './') {
return new URL('./', packageJSONUrl);
} else if (packageSubpath === '') {
return packageMainResolve(packageJSONUrl, packageConfig, base);
} else if (packageConfig.exports !== undefined) {
return packageExportsResolve(
packageJSONUrl, packageSubpath, packageConfig, base);
} else {
return finalizeResolution(
new URL(packageSubpath, packageJSONUrl), base);
}
// Cross-platform root check.
} while (packageJSONPath.length !== lastPath.length);
// eslint can't handle the above code.
// eslint-disable-next-line no-unreachable
throw new ERR_MODULE_NOT_FOUND(packageName, fileURLToPath(base));
}
function shouldBeTreatedAsRelativeOrAbsolutePath(specifier) {
if (specifier === '') return false;
if (specifier[0] === '/') return true;
if (specifier[0] === '.') {
if (specifier.length === 1 || specifier[1] === '/') return true;
if (specifier[1] === '.') {
if (specifier.length === 2 || specifier[2] === '/') return true;
}
}
return false;
}
function moduleResolve(specifier /* string */, base /* URL */) { /* -> URL */
// Order swapped from spec for minor perf gain.
// Ok since relative URLs cannot parse as URLs.
let resolved;
if (shouldBeTreatedAsRelativeOrAbsolutePath(specifier)) {
resolved = new URL(specifier, base);
} else {
try {
resolved = new URL(specifier);
} catch {
return packageResolve(specifier, base);
}
}
return finalizeResolution(resolved, base);
}
function defaultResolve(specifier, { parentURL } = {}, defaultResolveUnused) {
let parsed;
try {
parsed = new URL(specifier);
if (parsed.protocol === 'data:') {
return {
url: specifier
};
}
} catch {}
if (parsed && parsed.protocol === 'nodejs:')
return { url: specifier };
if (parsed && parsed.protocol !== 'file:' && parsed.protocol !== 'data:')
throw new ERR_UNSUPPORTED_ESM_URL_SCHEME();
if (NativeModule.canBeRequiredByUsers(specifier)) {
return {
url: 'nodejs:' + specifier
};
}
if (parentURL && StringPrototypeStartsWith(parentURL, 'data:')) {
// This is gonna blow up, we want the error
new URL(specifier, parentURL);
}
const isMain = parentURL === undefined;
if (isMain) {
parentURL = pathToFileURL(`${process.cwd()}/`).href;
// This is the initial entry point to the program, and --input-type has
// been passed as an option; but --input-type can only be used with
// --eval, --print or STDIN string input. It is not allowed with file
// input, to avoid user confusion over how expansive the effect of the
// flag should be (i.e. entry point only, package scope surrounding the
// entry point, etc.).
if (typeFlag)
throw new ERR_INPUT_TYPE_NOT_ALLOWED();
}
let url = moduleResolve(specifier, new URL(parentURL));
if (isMain ? !preserveSymlinksMain : !preserveSymlinks) {
const urlPath = fileURLToPath(url);
const real = realpathSync(urlPath, {
// [internalFS.realpathCacheKey]: realpathCache
});
const old = url;
url = pathToFileURL(real + (urlPath.endsWith(sep) ? '/' : ''));
url.search = old.search;
url.hash = old.hash;
}
return { url: `${url}` };
}
return {
defaultResolve,
getPackageType
};
}
module.exports = {
createResolve
}
-2
View File
@@ -1,2 +0,0 @@
#!/usr/bin/env node
export {};
-7
View File
@@ -1,7 +0,0 @@
#!/usr/bin/env node
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const bin_1 = require("./bin");
console.warn('ts-script has been deprecated and will be removed in the next major release.', 'Please use ts-node-script instead');
bin_1.main(['--script-mode', ...process.argv.slice(2)]);
//# sourceMappingURL=bin-script-deprecated.js.map
-1
View File
@@ -1 +0,0 @@
{"version":3,"file":"bin-script-deprecated.js","sourceRoot":"","sources":["../src/bin-script-deprecated.ts"],"names":[],"mappings":";;;AAEA,+BAA4B;AAE5B,OAAO,CAAC,IAAI,CACV,8EAA8E,EAC9E,mCAAmC,CACpC,CAAA;AAED,UAAI,CAAC,CAAC,eAAe,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAA","sourcesContent":["#!/usr/bin/env node\n\nimport { main } from './bin'\n\nconsole.warn(\n 'ts-script has been deprecated and will be removed in the next major release.',\n 'Please use ts-node-script instead'\n)\n\nmain(['--script-mode', ...process.argv.slice(2)])\n"]}
-2
View File
@@ -1,2 +0,0 @@
#!/usr/bin/env node
export {};
-6
View File
@@ -1,6 +0,0 @@
#!/usr/bin/env node
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const bin_1 = require("./bin");
bin_1.main(['--script-mode', ...process.argv.slice(2)]);
//# sourceMappingURL=bin-script.js.map
-1
View File
@@ -1 +0,0 @@
{"version":3,"file":"bin-script.js","sourceRoot":"","sources":["../src/bin-script.ts"],"names":[],"mappings":";;;AAEA,+BAA4B;AAE5B,UAAI,CAAC,CAAC,eAAe,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAA","sourcesContent":["#!/usr/bin/env node\n\nimport { main } from './bin'\n\nmain(['--script-mode', ...process.argv.slice(2)])\n"]}
-2
View File
@@ -1,2 +0,0 @@
#!/usr/bin/env node
export {};
-6
View File
@@ -1,6 +0,0 @@
#!/usr/bin/env node
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const bin_1 = require("./bin");
bin_1.main(['--transpile-only', ...process.argv.slice(2)]);
//# sourceMappingURL=bin-transpile.js.map
-1
View File
@@ -1 +0,0 @@
{"version":3,"file":"bin-transpile.js","sourceRoot":"","sources":["../src/bin-transpile.ts"],"names":[],"mappings":";;;AAEA,+BAA4B;AAE5B,UAAI,CAAC,CAAC,kBAAkB,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAA","sourcesContent":["#!/usr/bin/env node\n\nimport { main } from './bin'\n\nmain(['--transpile-only', ...process.argv.slice(2)])\n"]}
-5
View File
@@ -1,5 +0,0 @@
#!/usr/bin/env node
/**
* Main `bin` functionality.
*/
export declare function main(argv: string[]): void;
-448
View File
@@ -1,448 +0,0 @@
#!/usr/bin/env node
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const path_1 = require("path");
const repl_1 = require("repl");
const util_1 = require("util");
const Module = require("module");
const arg = require("arg");
const diff_1 = require("diff");
const vm_1 = require("vm");
const fs_1 = require("fs");
const os_1 = require("os");
const index_1 = require("./index");
/**
* Eval filename for REPL/debug.
*/
const EVAL_FILENAME = `[eval].ts`;
/**
* Eval state management.
*/
class EvalState {
constructor(path) {
this.path = path;
this.input = '';
this.output = '';
this.version = 0;
this.lines = 0;
}
}
/**
* Main `bin` functionality.
*/
function main(argv) {
const args = arg({
// Node.js-like options.
'--eval': String,
'--interactive': Boolean,
'--print': Boolean,
'--require': [String],
// CLI options.
'--help': Boolean,
'--script-mode': Boolean,
'--version': arg.COUNT,
// Project options.
'--dir': String,
'--files': Boolean,
'--compiler': String,
'--compiler-options': index_1.parse,
'--project': String,
'--ignore-diagnostics': [String],
'--ignore': [String],
'--transpile-only': Boolean,
'--type-check': Boolean,
'--compiler-host': Boolean,
'--pretty': Boolean,
'--skip-project': Boolean,
'--skip-ignore': Boolean,
'--prefer-ts-exts': Boolean,
'--log-error': Boolean,
'--emit': Boolean,
// Aliases.
'-e': '--eval',
'-i': '--interactive',
'-p': '--print',
'-r': '--require',
'-h': '--help',
'-s': '--script-mode',
'-v': '--version',
'-T': '--transpile-only',
'-H': '--compiler-host',
'-I': '--ignore',
'-P': '--project',
'-C': '--compiler',
'-D': '--ignore-diagnostics',
'-O': '--compiler-options'
}, {
argv,
stopAtPositional: true
});
// Only setting defaults for CLI-specific flags
// Anything passed to `register()` can be `undefined`; `create()` will apply
// defaults.
const { '--dir': dir, '--help': help = false, '--script-mode': scriptMode = false, '--version': version = 0, '--require': requires = [], '--eval': code = undefined, '--print': print = false, '--interactive': interactive = false, '--files': files, '--compiler': compiler, '--compiler-options': compilerOptions, '--project': project, '--ignore-diagnostics': ignoreDiagnostics, '--ignore': ignore, '--transpile-only': transpileOnly, '--type-check': typeCheck, '--compiler-host': compilerHost, '--pretty': pretty, '--skip-project': skipProject, '--skip-ignore': skipIgnore, '--prefer-ts-exts': preferTsExts, '--log-error': logError, '--emit': emit } = args;
if (help) {
console.log(`
Usage: ts-node [options] [ -e script | script.ts ] [arguments]
Options:
-e, --eval [code] Evaluate code
-p, --print Print result of \`--eval\`
-r, --require [path] Require a node module before execution
-i, --interactive Opens the REPL even if stdin does not appear to be a terminal
-h, --help Print CLI usage
-v, --version Print module version information
-s, --script-mode Use cwd from <script.ts> instead of current directory
-T, --transpile-only Use TypeScript's faster \`transpileModule\`
-H, --compiler-host Use TypeScript's compiler host API
-I, --ignore [pattern] Override the path patterns to skip compilation
-P, --project [path] Path to TypeScript JSON project file
-C, --compiler [name] Specify a custom TypeScript compiler
-D, --ignore-diagnostics [code] Ignore TypeScript warnings by diagnostic code
-O, --compiler-options [opts] JSON object to merge with compiler options
--dir Specify working directory for config resolution
--scope Scope compiler to files within \`cwd\` only
--files Load \`files\`, \`include\` and \`exclude\` from \`tsconfig.json\` on startup
--pretty Use pretty diagnostic formatter (usually enabled by default)
--skip-project Skip reading \`tsconfig.json\`
--skip-ignore Skip \`--ignore\` checks
--prefer-ts-exts Prefer importing TypeScript files over JavaScript files
--log-error Logs TypeScript errors to stderr instead of throwing exceptions
`);
process.exit(0);
}
// Output project information.
if (version === 1) {
console.log(`v${index_1.VERSION}`);
process.exit(0);
}
const cwd = dir || process.cwd();
/** Unresolved. May point to a symlink, not realpath. May be missing file extension */
const scriptPath = args._.length ? path_1.resolve(cwd, args._[0]) : undefined;
const state = new EvalState(scriptPath || path_1.join(cwd, EVAL_FILENAME));
// Register the TypeScript compiler instance.
const service = index_1.register({
dir: getCwd(dir, scriptMode, scriptPath),
emit,
files,
pretty,
transpileOnly,
typeCheck,
compilerHost,
ignore,
preferTsExts,
logError,
project,
skipProject,
skipIgnore,
compiler,
ignoreDiagnostics,
compilerOptions,
readFile: code !== undefined
? (path) => {
if (path === state.path)
return state.input;
try {
return fs_1.readFileSync(path, 'utf8');
}
catch (err) { /* Ignore. */ }
}
: undefined,
fileExists: code !== undefined
? (path) => {
if (path === state.path)
return true;
try {
const stats = fs_1.statSync(path);
return stats.isFile() || stats.isFIFO();
}
catch (err) {
return false;
}
}
: undefined
});
// Output project information.
if (version >= 2) {
console.log(`ts-node v${index_1.VERSION}`);
console.log(`node ${process.version}`);
console.log(`compiler v${service.ts.version}`);
process.exit(0);
}
// Create a local module instance based on `cwd`.
const module = new Module(state.path);
module.filename = state.path;
module.paths = Module._nodeModulePaths(cwd);
Module._preloadModules(requires);
// Prepend `ts-node` arguments to CLI for child processes.
process.execArgv.unshift(__filename, ...process.argv.slice(2, process.argv.length - args._.length));
process.argv = [process.argv[1]].concat(scriptPath || []).concat(args._.slice(1));
// Execute the main contents (either eval, script or piped).
if (code !== undefined && !interactive) {
evalAndExit(service, state, module, code, print);
}
else {
if (args._.length) {
Module.runMain();
}
else {
// Piping of execution _only_ occurs when no other script is specified.
// --interactive flag forces REPL
if (interactive || process.stdin.isTTY) {
startRepl(service, state, code);
}
else {
let buffer = code || '';
process.stdin.on('data', (chunk) => buffer += chunk);
process.stdin.on('end', () => evalAndExit(service, state, module, buffer, print));
}
}
}
}
exports.main = main;
/**
* Get project path from args.
*/
function getCwd(dir, scriptMode, scriptPath) {
// Validate `--script-mode` usage is correct.
if (scriptMode) {
if (!scriptPath) {
throw new TypeError('Script mode must be used with a script name, e.g. `ts-node -s <script.ts>`');
}
if (dir) {
throw new TypeError('Script mode cannot be combined with `--dir`');
}
// Use node's own resolution behavior to ensure we follow symlinks.
// scriptPath may omit file extension or point to a directory with or without package.json.
// This happens before we are registered, so we tell node's resolver to consider ts, tsx, and jsx files.
// In extremely rare cases, is is technically possible to resolve the wrong directory,
// because we do not yet know preferTsExts, jsx, nor allowJs.
// See also, justification why this will not happen in real-world situations:
// https://github.com/TypeStrong/ts-node/pull/1009#issuecomment-613017081
const exts = ['.js', '.jsx', '.ts', '.tsx'];
const extsTemporarilyInstalled = [];
for (const ext of exts) {
if (!hasOwnProperty(require.extensions, ext)) { // tslint:disable-line
extsTemporarilyInstalled.push(ext);
require.extensions[ext] = function () { }; // tslint:disable-line
}
}
try {
return path_1.dirname(require.resolve(scriptPath));
}
finally {
for (const ext of extsTemporarilyInstalled) {
delete require.extensions[ext]; // tslint:disable-line
}
}
}
return dir;
}
/**
* Evaluate a script.
*/
function evalAndExit(service, state, module, code, isPrinted) {
let result;
global.__filename = module.filename;
global.__dirname = path_1.dirname(module.filename);
global.exports = module.exports;
global.module = module;
global.require = module.require.bind(module);
try {
result = _eval(service, state, code);
}
catch (error) {
if (error instanceof index_1.TSError) {
console.error(error);
process.exit(1);
}
throw error;
}
if (isPrinted) {
console.log(typeof result === 'string' ? result : util_1.inspect(result));
}
}
/**
* Evaluate the code snippet.
*/
function _eval(service, state, input) {
const lines = state.lines;
const isCompletion = !/\n$/.test(input);
const undo = appendEval(state, input);
let output;
try {
output = service.compile(state.input, state.path, -lines);
}
catch (err) {
undo();
throw err;
}
// Use `diff` to check for new JavaScript to execute.
const changes = diff_1.diffLines(state.output, output);
if (isCompletion) {
undo();
}
else {
state.output = output;
}
return changes.reduce((result, change) => {
return change.added ? exec(change.value, state.path) : result;
}, undefined);
}
/**
* Execute some code.
*/
function exec(code, filename) {
const script = new vm_1.Script(code, { filename: filename });
return script.runInThisContext();
}
/**
* Start a CLI REPL.
*/
function startRepl(service, state, code) {
// Eval incoming code before the REPL starts.
if (code) {
try {
_eval(service, state, `${code}\n`);
}
catch (err) {
console.error(err);
process.exit(1);
}
}
const repl = repl_1.start({
prompt: '> ',
input: process.stdin,
output: process.stdout,
terminal: process.stdout.isTTY,
eval: replEval,
useGlobal: true
});
/**
* Eval code from the REPL.
*/
function replEval(code, _context, _filename, callback) {
let err = null;
let result;
// TODO: Figure out how to handle completion here.
if (code === '.scope') {
callback(err);
return;
}
try {
result = _eval(service, state, code);
}
catch (error) {
if (error instanceof index_1.TSError) {
// Support recoverable compilations using >= node 6.
if (repl_1.Recoverable && isRecoverable(error)) {
err = new repl_1.Recoverable(error);
}
else {
console.error(error);
}
}
else {
err = error;
}
}
return callback(err, result);
}
// Bookmark the point where we should reset the REPL state.
const resetEval = appendEval(state, '');
function reset() {
resetEval();
// Hard fix for TypeScript forcing `Object.defineProperty(exports, ...)`.
exec('exports = module.exports', state.path);
}
reset();
repl.on('reset', reset);
repl.defineCommand('type', {
help: 'Check the type of a TypeScript identifier',
action: function (identifier) {
if (!identifier) {
repl.displayPrompt();
return;
}
const undo = appendEval(state, identifier);
const { name, comment } = service.getTypeInfo(state.input, state.path, state.input.length);
undo();
if (name)
repl.outputStream.write(`${name}\n`);
if (comment)
repl.outputStream.write(`${comment}\n`);
repl.displayPrompt();
}
});
// Set up REPL history when available natively via node.js >= 11.
if (repl.setupHistory) {
const historyPath = process.env.TS_NODE_HISTORY || path_1.join(os_1.homedir(), '.ts_node_repl_history');
repl.setupHistory(historyPath, err => {
if (!err)
return;
console.error(err);
process.exit(1);
});
}
}
/**
* Append to the eval instance and return an undo function.
*/
function appendEval(state, input) {
const undoInput = state.input;
const undoVersion = state.version;
const undoOutput = state.output;
const undoLines = state.lines;
// Handle ASI issues with TypeScript re-evaluation.
if (undoInput.charAt(undoInput.length - 1) === '\n' && /^\s*[\/\[(`-]/.test(input) && !/;\s*$/.test(undoInput)) {
state.input = `${state.input.slice(0, -1)};\n`;
}
state.input += input;
state.lines += lineCount(input);
state.version++;
return function () {
state.input = undoInput;
state.output = undoOutput;
state.version = undoVersion;
state.lines = undoLines;
};
}
/**
* Count the number of lines.
*/
function lineCount(value) {
let count = 0;
for (const char of value) {
if (char === '\n') {
count++;
}
}
return count;
}
const RECOVERY_CODES = new Set([
1003,
1005,
1109,
1126,
1160,
1161,
2355 // "A function whose declared type is neither 'void' nor 'any' must return a value."
]);
/**
* Check if a function can recover gracefully.
*/
function isRecoverable(error) {
return error.diagnosticCodes.every(code => RECOVERY_CODES.has(code));
}
/** Safe `hasOwnProperty` */
function hasOwnProperty(object, property) {
return Object.prototype.hasOwnProperty.call(object, property);
}
if (require.main === module) {
main(process.argv.slice(2));
}
//# sourceMappingURL=bin.js.map
-1
View File
File diff suppressed because one or more lines are too long
-18
View File
@@ -1,18 +0,0 @@
/// <reference types="node" />
import { RegisterOptions } from './index';
export declare function registerAndCreateEsmHooks(opts?: RegisterOptions): {
resolve: (specifier: string, context: {
parentURL: string;
}, defaultResolve: any) => Promise<{
url: string;
}>;
getFormat: (url: string, context: {}, defaultGetFormat: any) => Promise<{
format: "json" | "module" | "builtin" | "commonjs" | "dynamic" | "wasm";
}>;
transformSource: (source: string | Buffer, context: {
url: string;
format: "json" | "module" | "builtin" | "commonjs" | "dynamic" | "wasm";
}, defaultTransformSource: any) => Promise<{
source: string | Buffer;
}>;
};
-89
View File
@@ -1,89 +0,0 @@
"use strict";
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
Object.defineProperty(exports, "__esModule", { value: true });
const index_1 = require("./index");
const url_1 = require("url");
const path_1 = require("path");
const assert = require("assert");
const { createResolve } = require('../dist-raw/node-esm-resolve-implementation');
// Note: On Windows, URLs look like this: file:///D:/dev/@TypeStrong/ts-node-examples/foo.ts
function registerAndCreateEsmHooks(opts) {
// Automatically performs registration just like `-r ts-node/register`
const tsNodeInstance = index_1.register(opts);
// Custom implementation that considers additional file extensions and automatically adds file extensions
const nodeResolveImplementation = createResolve(Object.assign(Object.assign({}, index_1.getExtensions(tsNodeInstance.config)), { preferTsExts: tsNodeInstance.options.preferTsExts }));
return { resolve, getFormat, transformSource };
function isFileUrlOrNodeStyleSpecifier(parsed) {
// We only understand file:// URLs, but in node, the specifier can be a node-style `./foo` or `foo`
const { protocol } = parsed;
return protocol === null || protocol === 'file:';
}
function resolve(specifier, context, defaultResolve) {
return __awaiter(this, void 0, void 0, function* () {
const defer = () => __awaiter(this, void 0, void 0, function* () {
const r = yield defaultResolve(specifier, context, defaultResolve);
return r;
});
const parsed = url_1.parse(specifier);
const { pathname, protocol, hostname } = parsed;
if (!isFileUrlOrNodeStyleSpecifier(parsed)) {
return defer();
}
if (protocol !== null && protocol !== 'file:') {
return defer();
}
// Malformed file:// URL? We should always see `null` or `''`
if (hostname) {
// TODO file://./foo sets `hostname` to `'.'`. Perhaps we should special-case this.
return defer();
}
// pathname is the path to be resolved
return nodeResolveImplementation.defaultResolve(specifier, context, defaultResolve);
});
}
function getFormat(url, context, defaultGetFormat) {
return __awaiter(this, void 0, void 0, function* () {
const defer = (overrideUrl = url) => defaultGetFormat(overrideUrl, context, defaultGetFormat);
const parsed = url_1.parse(url);
if (!isFileUrlOrNodeStyleSpecifier(parsed)) {
return defer();
}
const { pathname } = parsed;
assert(pathname !== null, 'ESM getFormat() hook: URL should never have null pathname');
const nativePath = url_1.fileURLToPath(url);
// If file has .ts, .tsx, or .jsx extension, then ask node how it would treat this file if it were .js
const ext = path_1.extname(nativePath);
if (ext === '.ts' || ext === '.tsx' || ext === '.jsx') {
return defer(url_1.format(url_1.pathToFileURL(nativePath + '.js')));
}
return defer();
});
}
function transformSource(source, context, defaultTransformSource) {
return __awaiter(this, void 0, void 0, function* () {
const defer = () => defaultTransformSource(source, context, defaultTransformSource);
const sourceAsString = typeof source === 'string' ? source : source.toString('utf8');
const { url } = context;
const parsed = url_1.parse(url);
if (!isFileUrlOrNodeStyleSpecifier(parsed)) {
return defer();
}
const nativePath = url_1.fileURLToPath(url);
if (tsNodeInstance.ignored(nativePath)) {
return defer();
}
const emittedJs = tsNodeInstance.compile(sourceAsString, nativePath);
return { source: emittedJs };
});
}
}
exports.registerAndCreateEsmHooks = registerAndCreateEsmHooks;
//# sourceMappingURL=esm.js.map
-1
View File
File diff suppressed because one or more lines are too long
-211
View File
@@ -1,211 +0,0 @@
import { BaseError } from 'make-error';
import * as _ts from 'typescript';
/**
* Registered `ts-node` instance information.
*/
export declare const REGISTER_INSTANCE: unique symbol;
/**
* Expose `REGISTER_INSTANCE` information on node.js `process`.
*/
declare global {
namespace NodeJS {
interface Process {
[REGISTER_INSTANCE]?: Register;
}
}
}
/**
* Common TypeScript interfaces between versions.
*/
export interface TSCommon {
version: typeof _ts.version;
sys: typeof _ts.sys;
ScriptSnapshot: typeof _ts.ScriptSnapshot;
displayPartsToString: typeof _ts.displayPartsToString;
createLanguageService: typeof _ts.createLanguageService;
getDefaultLibFilePath: typeof _ts.getDefaultLibFilePath;
getPreEmitDiagnostics: typeof _ts.getPreEmitDiagnostics;
flattenDiagnosticMessageText: typeof _ts.flattenDiagnosticMessageText;
transpileModule: typeof _ts.transpileModule;
ModuleKind: typeof _ts.ModuleKind;
ScriptTarget: typeof _ts.ScriptTarget;
findConfigFile: typeof _ts.findConfigFile;
readConfigFile: typeof _ts.readConfigFile;
parseJsonConfigFileContent: typeof _ts.parseJsonConfigFileContent;
formatDiagnostics: typeof _ts.formatDiagnostics;
formatDiagnosticsWithColorAndContext: typeof _ts.formatDiagnosticsWithColorAndContext;
}
/**
* Export the current version.
*/
export declare const VERSION: any;
/**
* Options for creating a new TypeScript compiler instance.
*/
export interface CreateOptions {
/**
* Specify working directory for config resolution.
*
* @default process.cwd()
*/
dir?: string;
/**
* Emit output files into `.ts-node` directory.
*
* @default false
*/
emit?: boolean;
/**
* Scope compiler to files within `cwd`.
*
* @default false
*/
scope?: boolean;
/**
* Use pretty diagnostic formatter.
*
* @default false
*/
pretty?: boolean;
/**
* Use TypeScript's faster `transpileModule`.
*
* @default false
*/
transpileOnly?: boolean;
/**
* **DEPRECATED** Specify type-check is enabled (e.g. `transpileOnly == false`).
*
* @default true
*/
typeCheck?: boolean;
/**
* Use TypeScript's compiler host API.
*
* @default false
*/
compilerHost?: boolean;
/**
* Logs TypeScript errors to stderr instead of throwing exceptions.
*
* @default false
*/
logError?: boolean;
/**
* Load files from `tsconfig.json` on startup.
*
* @default false
*/
files?: boolean;
/**
* Specify a custom TypeScript compiler.
*
* @default "typescript"
*/
compiler?: string;
/**
* Override the path patterns to skip compilation.
*
* @default /node_modules/
* @docsDefault "/node_modules/"
*/
ignore?: string[];
/**
* Path to TypeScript JSON project file.
*/
project?: string;
/**
* Skip project config resolution and loading.
*
* @default false
*/
skipProject?: boolean;
/**
* Skip ignore check.
*
* @default false
*/
skipIgnore?: boolean;
/**
* JSON object to merge with compiler options.
*
* @allOf [{"$ref": "https://schemastore.azurewebsites.net/schemas/json/tsconfig.json#definitions/compilerOptionsDefinition/properties/compilerOptions"}]
*/
compilerOptions?: object;
/**
* Ignore TypeScript warnings by diagnostic code.
*/
ignoreDiagnostics?: Array<number | string>;
readFile?: (path: string) => string | undefined;
fileExists?: (path: string) => boolean;
transformers?: _ts.CustomTransformers | ((p: _ts.Program) => _ts.CustomTransformers);
}
/**
* Options for registering a TypeScript compiler instance globally.
*/
export interface RegisterOptions extends CreateOptions {
/**
* Re-order file extensions so that TypeScript imports are preferred.
*
* @default false
*/
preferTsExts?: boolean;
}
/**
* Must be an interface to support `typescript-json-schema`.
*/
export interface TsConfigOptions extends Omit<RegisterOptions, 'transformers' | 'readFile' | 'fileExists' | 'skipProject' | 'project' | 'dir'> {
}
/**
* Information retrieved from type info check.
*/
export interface TypeInfo {
name: string;
comment: string;
}
/**
* Default register options, including values specified via environment
* variables.
*/
export declare const DEFAULTS: RegisterOptions;
/**
* Split a string array of values.
*/
export declare function split(value: string | undefined): string[] | undefined;
/**
* Parse a string as JSON.
*/
export declare function parse(value: string | undefined): object | undefined;
/**
* Replace backslashes with forward slashes.
*/
export declare function normalizeSlashes(value: string): string;
/**
* TypeScript diagnostics error.
*/
export declare class TSError extends BaseError {
diagnosticText: string;
diagnosticCodes: number[];
name: string;
constructor(diagnosticText: string, diagnosticCodes: number[]);
}
/**
* Return type for registering `ts-node`.
*/
export interface Register {
ts: TSCommon;
config: _ts.ParsedCommandLine;
options: RegisterOptions;
enabled(enabled?: boolean): boolean;
ignored(fileName: string): boolean;
compile(code: string, fileName: string, lineOffset?: number): string;
getTypeInfo(code: string, fileName: string, position: number): TypeInfo;
}
/**
* Register TypeScript compiler instance onto node.js
*/
export declare function register(opts?: RegisterOptions): Register;
/**
* Create TypeScript compiler instance.
*/
export declare function create(rawOptions?: CreateOptions): Register;
-674
View File
@@ -1,674 +0,0 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const path_1 = require("path");
const sourceMapSupport = require("source-map-support");
const ynModule = require("yn");
const make_error_1 = require("make-error");
const util = require("util");
/**
* Registered `ts-node` instance information.
*/
exports.REGISTER_INSTANCE = Symbol.for('ts-node.register.instance');
/**
* @internal
*/
exports.INSPECT_CUSTOM = util.inspect.custom || 'inspect';
/**
* Wrapper around yn module that returns `undefined` instead of `null`.
* This is implemented by yn v4, but we're staying on v3 to avoid v4's node 10 requirement.
*/
function yn(value) {
var _a;
return (_a = ynModule(value)) !== null && _a !== void 0 ? _a : undefined;
}
/**
* Debugging `ts-node`.
*/
const shouldDebug = yn(process.env.TS_NODE_DEBUG);
/** @internal */
exports.debug = shouldDebug ?
(...args) => console.log(`[ts-node ${new Date().toISOString()}]`, ...args)
: () => undefined;
const debugFn = shouldDebug ?
(key, fn) => {
let i = 0;
return (x) => {
exports.debug(key, x, ++i);
return fn(x);
};
} :
(_, fn) => fn;
/**
* Export the current version.
*/
exports.VERSION = require('../package.json').version;
/**
* Like `Object.assign`, but ignores `undefined` properties.
*/
function assign(initialValue, ...sources) {
for (const source of sources) {
for (const key of Object.keys(source)) {
const value = source[key];
if (value !== undefined)
initialValue[key] = value;
}
}
return initialValue;
}
/**
* Default register options, including values specified via environment
* variables.
*/
exports.DEFAULTS = {
dir: process.env.TS_NODE_DIR,
emit: yn(process.env.TS_NODE_EMIT),
scope: yn(process.env.TS_NODE_SCOPE),
files: yn(process.env.TS_NODE_FILES),
pretty: yn(process.env.TS_NODE_PRETTY),
compiler: process.env.TS_NODE_COMPILER,
compilerOptions: parse(process.env.TS_NODE_COMPILER_OPTIONS),
ignore: split(process.env.TS_NODE_IGNORE),
project: process.env.TS_NODE_PROJECT,
skipProject: yn(process.env.TS_NODE_SKIP_PROJECT),
skipIgnore: yn(process.env.TS_NODE_SKIP_IGNORE),
preferTsExts: yn(process.env.TS_NODE_PREFER_TS_EXTS),
ignoreDiagnostics: split(process.env.TS_NODE_IGNORE_DIAGNOSTICS),
transpileOnly: yn(process.env.TS_NODE_TRANSPILE_ONLY),
typeCheck: yn(process.env.TS_NODE_TYPE_CHECK),
compilerHost: yn(process.env.TS_NODE_COMPILER_HOST),
logError: yn(process.env.TS_NODE_LOG_ERROR)
};
/**
* Default TypeScript compiler options required by `ts-node`.
*/
const TS_NODE_COMPILER_OPTIONS = {
sourceMap: true,
inlineSourceMap: false,
inlineSources: true,
declaration: false,
noEmit: false,
outDir: '.ts-node'
};
/**
* Split a string array of values.
*/
function split(value) {
return typeof value === 'string' ? value.split(/ *, */g) : undefined;
}
exports.split = split;
/**
* Parse a string as JSON.
*/
function parse(value) {
return typeof value === 'string' ? JSON.parse(value) : undefined;
}
exports.parse = parse;
/**
* Replace backslashes with forward slashes.
*/
function normalizeSlashes(value) {
return value.replace(/\\/g, '/');
}
exports.normalizeSlashes = normalizeSlashes;
/**
* TypeScript diagnostics error.
*/
class TSError extends make_error_1.BaseError {
constructor(diagnosticText, diagnosticCodes) {
super(` Unable to compile TypeScript:\n${diagnosticText}`);
this.diagnosticText = diagnosticText;
this.diagnosticCodes = diagnosticCodes;
this.name = 'TSError';
}
/**
* @internal
*/
[exports.INSPECT_CUSTOM]() {
return this.diagnosticText;
}
}
exports.TSError = TSError;
/**
* Cached fs operation wrapper.
*/
function cachedLookup(fn) {
const cache = new Map();
return (arg) => {
if (!cache.has(arg)) {
cache.set(arg, fn(arg));
}
return cache.get(arg);
};
}
/** @internal */
function getExtensions(config) {
const tsExtensions = ['.ts'];
const jsExtensions = [];
// Enable additional extensions when JSX or `allowJs` is enabled.
if (config.options.jsx)
tsExtensions.push('.tsx');
if (config.options.allowJs)
jsExtensions.push('.js');
if (config.options.jsx && config.options.allowJs)
jsExtensions.push('.jsx');
return { tsExtensions, jsExtensions };
}
exports.getExtensions = getExtensions;
/**
* Register TypeScript compiler instance onto node.js
*/
function register(opts = {}) {
const originalJsHandler = require.extensions['.js']; // tslint:disable-line
const service = create(opts);
const { tsExtensions, jsExtensions } = getExtensions(service.config);
const extensions = [...tsExtensions, ...jsExtensions];
// Expose registered instance globally.
process[exports.REGISTER_INSTANCE] = service;
// Register the extensions.
registerExtensions(service.options.preferTsExts, extensions, service, originalJsHandler);
return service;
}
exports.register = register;
/**
* Create TypeScript compiler instance.
*/
function create(rawOptions = {}) {
var _a, _b;
const dir = (_a = rawOptions.dir) !== null && _a !== void 0 ? _a : exports.DEFAULTS.dir;
const compilerName = (_b = rawOptions.compiler) !== null && _b !== void 0 ? _b : exports.DEFAULTS.compiler;
const cwd = dir ? path_1.resolve(dir) : process.cwd();
/**
* Load the typescript compiler. It is required to load the tsconfig but might
* be changed by the tsconfig, so we sometimes have to do this twice.
*/
function loadCompiler(name) {
const compiler = require.resolve(name || 'typescript', { paths: [cwd, __dirname] });
const ts = require(compiler);
return { compiler, ts };
}
// Compute minimum options to read the config file.
let { compiler, ts } = loadCompiler(compilerName);
// Read config file and merge new options between env and CLI options.
const { config, options: tsconfigOptions } = readConfig(cwd, ts, rawOptions);
const options = assign({}, exports.DEFAULTS, tsconfigOptions || {}, rawOptions);
// If `compiler` option changed based on tsconfig, re-load the compiler.
if (options.compiler !== compilerName) {
({ compiler, ts } = loadCompiler(options.compiler));
}
const readFile = options.readFile || ts.sys.readFile;
const fileExists = options.fileExists || ts.sys.fileExists;
const transpileOnly = options.transpileOnly === true || options.typeCheck === false;
const transformers = options.transformers || undefined;
const ignoreDiagnostics = [
6059,
18002,
18003,
...(options.ignoreDiagnostics || [])
].map(Number);
const configDiagnosticList = filterDiagnostics(config.errors, ignoreDiagnostics);
const outputCache = new Map();
const isScoped = options.scope ? (relname) => relname.charAt(0) !== '.' : () => true;
const shouldIgnore = createIgnore(options.skipIgnore ? [] : (options.ignore || ['(?:^|/)node_modules/']).map(str => new RegExp(str)));
const diagnosticHost = {
getNewLine: () => ts.sys.newLine,
getCurrentDirectory: () => cwd,
getCanonicalFileName: ts.sys.useCaseSensitiveFileNames ? x => x : x => x.toLowerCase()
};
// Install source map support and read from memory cache.
sourceMapSupport.install({
environment: 'node',
retrieveFile(path) {
var _a;
return ((_a = outputCache.get(normalizeSlashes(path))) === null || _a === void 0 ? void 0 : _a.content) || '';
}
});
const formatDiagnostics = process.stdout.isTTY || options.pretty
? (ts.formatDiagnosticsWithColorAndContext || ts.formatDiagnostics)
: ts.formatDiagnostics;
function createTSError(diagnostics) {
const diagnosticText = formatDiagnostics(diagnostics, diagnosticHost);
const diagnosticCodes = diagnostics.map(x => x.code);
return new TSError(diagnosticText, diagnosticCodes);
}
function reportTSError(configDiagnosticList) {
const error = createTSError(configDiagnosticList);
if (options.logError) {
// Print error in red color and continue execution.
console.error('\x1b[31m%s\x1b[0m', error);
}
else {
// Throw error and exit the script.
throw error;
}
}
// Render the configuration errors.
if (configDiagnosticList.length)
reportTSError(configDiagnosticList);
/**
* Get the extension for a transpiled file.
*/
const getExtension = config.options.jsx === ts.JsxEmit.Preserve ?
((path) => /\.[tj]sx$/.test(path) ? '.jsx' : '.js') :
((_) => '.js');
/**
* Create the basic required function using transpile mode.
*/
let getOutput;
let getTypeInfo;
const getOutputTranspileOnly = (code, fileName, overrideCompilerOptions) => {
const result = ts.transpileModule(code, {
fileName,
compilerOptions: overrideCompilerOptions ? Object.assign(Object.assign({}, config.options), overrideCompilerOptions) : config.options,
reportDiagnostics: true
});
const diagnosticList = filterDiagnostics(result.diagnostics || [], ignoreDiagnostics);
if (diagnosticList.length)
reportTSError(diagnosticList);
return [result.outputText, result.sourceMapText];
};
// Use full language services when the fast option is disabled.
if (!transpileOnly) {
const fileContents = new Map();
const rootFileNames = config.fileNames.slice();
const cachedReadFile = cachedLookup(debugFn('readFile', readFile));
// Use language services by default (TODO: invert next major version).
if (!options.compilerHost) {
let projectVersion = 1;
const fileVersions = new Map(rootFileNames.map(fileName => [fileName, 0]));
const getCustomTransformers = () => {
if (typeof transformers === 'function') {
const program = service.getProgram();
return program ? transformers(program) : undefined;
}
return transformers;
};
// Create the compiler host for type checking.
const serviceHost = {
getProjectVersion: () => String(projectVersion),
getScriptFileNames: () => Array.from(fileVersions.keys()),
getScriptVersion: (fileName) => {
const version = fileVersions.get(fileName);
return version ? version.toString() : '';
},
getScriptSnapshot(fileName) {
let contents = fileContents.get(fileName);
// Read contents into TypeScript memory cache.
if (contents === undefined) {
contents = cachedReadFile(fileName);
if (contents === undefined)
return;
fileVersions.set(fileName, 1);
fileContents.set(fileName, contents);
}
return ts.ScriptSnapshot.fromString(contents);
},
readFile: cachedReadFile,
readDirectory: ts.sys.readDirectory,
getDirectories: cachedLookup(debugFn('getDirectories', ts.sys.getDirectories)),
fileExists: cachedLookup(debugFn('fileExists', fileExists)),
directoryExists: cachedLookup(debugFn('directoryExists', ts.sys.directoryExists)),
getNewLine: () => ts.sys.newLine,
useCaseSensitiveFileNames: () => ts.sys.useCaseSensitiveFileNames,
getCurrentDirectory: () => cwd,
getCompilationSettings: () => config.options,
getDefaultLibFileName: () => ts.getDefaultLibFilePath(config.options),
getCustomTransformers: getCustomTransformers
};
const registry = ts.createDocumentRegistry(ts.sys.useCaseSensitiveFileNames, cwd);
const service = ts.createLanguageService(serviceHost, registry);
const updateMemoryCache = (contents, fileName) => {
// Add to `rootFiles` when discovered for the first time.
if (!fileVersions.has(fileName)) {
rootFileNames.push(fileName);
}
const previousVersion = fileVersions.get(fileName) || 0;
const previousContents = fileContents.get(fileName);
// Avoid incrementing cache when nothing has changed.
if (contents !== previousContents) {
fileVersions.set(fileName, previousVersion + 1);
fileContents.set(fileName, contents);
// Increment project version for every file change.
projectVersion++;
}
};
let previousProgram = undefined;
getOutput = (code, fileName) => {
updateMemoryCache(code, fileName);
const programBefore = service.getProgram();
if (programBefore !== previousProgram) {
exports.debug(`compiler rebuilt Program instance when getting output for ${fileName}`);
}
const output = service.getEmitOutput(fileName);
// Get the relevant diagnostics - this is 3x faster than `getPreEmitDiagnostics`.
const diagnostics = service.getSemanticDiagnostics(fileName)
.concat(service.getSyntacticDiagnostics(fileName));
const programAfter = service.getProgram();
exports.debug('invariant: Is service.getProject() identical before and after getting emit output and diagnostics? (should always be true) ', programBefore === programAfter);
previousProgram = programAfter;
const diagnosticList = filterDiagnostics(diagnostics, ignoreDiagnostics);
if (diagnosticList.length)
reportTSError(diagnosticList);
if (output.emitSkipped) {
throw new TypeError(`${path_1.relative(cwd, fileName)}: Emit skipped`);
}
// Throw an error when requiring `.d.ts` files.
if (output.outputFiles.length === 0) {
throw new TypeError(`Unable to require file: ${path_1.relative(cwd, fileName)}\n` +
'This is usually the result of a faulty configuration or import. ' +
'Make sure there is a `.js`, `.json` or other executable extension with ' +
'loader attached before `ts-node` available.');
}
return [output.outputFiles[1].text, output.outputFiles[0].text];
};
getTypeInfo = (code, fileName, position) => {
updateMemoryCache(code, fileName);
const info = service.getQuickInfoAtPosition(fileName, position);
const name = ts.displayPartsToString(info ? info.displayParts : []);
const comment = ts.displayPartsToString(info ? info.documentation : []);
return { name, comment };
};
}
else {
const sys = Object.assign(Object.assign(Object.assign({}, ts.sys), diagnosticHost), { readFile: (fileName) => {
const cacheContents = fileContents.get(fileName);
if (cacheContents !== undefined)
return cacheContents;
return cachedReadFile(fileName);
}, readDirectory: ts.sys.readDirectory, getDirectories: cachedLookup(debugFn('getDirectories', ts.sys.getDirectories)), fileExists: cachedLookup(debugFn('fileExists', fileExists)), directoryExists: cachedLookup(debugFn('directoryExists', ts.sys.directoryExists)), resolvePath: cachedLookup(debugFn('resolvePath', ts.sys.resolvePath)), realpath: ts.sys.realpath ? cachedLookup(debugFn('realpath', ts.sys.realpath)) : undefined });
const host = ts.createIncrementalCompilerHost
? ts.createIncrementalCompilerHost(config.options, sys)
: Object.assign(Object.assign({}, sys), { getSourceFile: (fileName, languageVersion) => {
const contents = sys.readFile(fileName);
if (contents === undefined)
return;
return ts.createSourceFile(fileName, contents, languageVersion);
}, getDefaultLibLocation: () => normalizeSlashes(path_1.dirname(compiler)), getDefaultLibFileName: () => normalizeSlashes(path_1.join(path_1.dirname(compiler), ts.getDefaultLibFileName(config.options))), useCaseSensitiveFileNames: () => sys.useCaseSensitiveFileNames });
// Fallback for older TypeScript releases without incremental API.
let builderProgram = ts.createIncrementalProgram
? ts.createIncrementalProgram({
rootNames: rootFileNames.slice(),
options: config.options,
host: host,
configFileParsingDiagnostics: config.errors,
projectReferences: config.projectReferences
})
: ts.createEmitAndSemanticDiagnosticsBuilderProgram(rootFileNames.slice(), config.options, host, undefined, config.errors, config.projectReferences);
// Read and cache custom transformers.
const customTransformers = typeof transformers === 'function'
? transformers(builderProgram.getProgram())
: transformers;
// Set the file contents into cache manually.
const updateMemoryCache = (contents, fileName) => {
const sourceFile = builderProgram.getSourceFile(fileName);
fileContents.set(fileName, contents);
// Add to `rootFiles` when discovered by compiler for the first time.
if (sourceFile === undefined) {
rootFileNames.push(fileName);
}
// Update program when file changes.
if (sourceFile === undefined || sourceFile.text !== contents) {
builderProgram = ts.createEmitAndSemanticDiagnosticsBuilderProgram(rootFileNames.slice(), config.options, host, builderProgram, config.errors, config.projectReferences);
}
};
getOutput = (code, fileName) => {
const output = ['', ''];
updateMemoryCache(code, fileName);
const sourceFile = builderProgram.getSourceFile(fileName);
if (!sourceFile)
throw new TypeError(`Unable to read file: ${fileName}`);
const program = builderProgram.getProgram();
const diagnostics = ts.getPreEmitDiagnostics(program, sourceFile);
const diagnosticList = filterDiagnostics(diagnostics, ignoreDiagnostics);
if (diagnosticList.length)
reportTSError(diagnosticList);
const result = builderProgram.emit(sourceFile, (path, file, writeByteOrderMark) => {
if (path.endsWith('.map')) {
output[1] = file;
}
else {
output[0] = file;
}
if (options.emit)
sys.writeFile(path, file, writeByteOrderMark);
}, undefined, undefined, customTransformers);
if (result.emitSkipped) {
throw new TypeError(`${path_1.relative(cwd, fileName)}: Emit skipped`);
}
// Throw an error when requiring files that cannot be compiled.
if (output[0] === '') {
if (program.isSourceFileFromExternalLibrary(sourceFile)) {
throw new TypeError(`Unable to compile file from external library: ${path_1.relative(cwd, fileName)}`);
}
throw new TypeError(`Unable to require file: ${path_1.relative(cwd, fileName)}\n` +
'This is usually the result of a faulty configuration or import. ' +
'Make sure there is a `.js`, `.json` or other executable extension with ' +
'loader attached before `ts-node` available.');
}
return output;
};
getTypeInfo = (code, fileName, position) => {
updateMemoryCache(code, fileName);
const sourceFile = builderProgram.getSourceFile(fileName);
if (!sourceFile)
throw new TypeError(`Unable to read file: ${fileName}`);
const node = getTokenAtPosition(ts, sourceFile, position);
const checker = builderProgram.getProgram().getTypeChecker();
const symbol = checker.getSymbolAtLocation(node);
if (!symbol)
return { name: '', comment: '' };
const type = checker.getTypeOfSymbolAtLocation(symbol, node);
const signatures = [...type.getConstructSignatures(), ...type.getCallSignatures()];
return {
name: signatures.length ? signatures.map(x => checker.signatureToString(x)).join('\n') : checker.typeToString(type),
comment: ts.displayPartsToString(symbol ? symbol.getDocumentationComment(checker) : [])
};
};
// Write `.tsbuildinfo` when `--build` is enabled.
if (options.emit && config.options.incremental) {
process.on('exit', () => {
// Emits `.tsbuildinfo` to filesystem.
builderProgram.getProgram().emitBuildInfo();
});
}
}
}
else {
if (typeof transformers === 'function') {
throw new TypeError('Transformers function is unavailable in "--transpile-only"');
}
getOutput = getOutputTranspileOnly;
getTypeInfo = () => {
throw new TypeError('Type information is unavailable in "--transpile-only"');
};
}
const cannotCompileViaBothCodepathsErrorMessage = 'Cannot compile the same file via both `require()` and ESM hooks codepaths. ' +
'This breaks source-map-support, which cannot tell the difference between the two sourcemaps. ' +
'To avoid this problem, load each .ts file as only ESM or only CommonJS.';
// Create a simple TypeScript compiler proxy.
function compile(code, fileName, lineOffset = 0) {
const normalizedFileName = normalizeSlashes(fileName);
const [value, sourceMap] = getOutput(code, normalizedFileName);
const output = updateOutput(value, normalizedFileName, sourceMap, getExtension);
outputCache.set(normalizedFileName, { content: output });
return output;
}
let active = true;
const enabled = (enabled) => enabled === undefined ? active : (active = !!enabled);
const ignored = (fileName) => {
if (!active)
return true;
const relname = path_1.relative(cwd, fileName);
if (!config.options.allowJs) {
const ext = path_1.extname(fileName);
if (ext === '.js' || ext === '.jsx')
return true;
}
return !isScoped(relname) || shouldIgnore(relname);
};
return { ts, config, compile, getTypeInfo, ignored, enabled, options };
}
exports.create = create;
/**
* Check if the filename should be ignored.
*/
function createIgnore(ignore) {
return (relname) => {
const path = normalizeSlashes(relname);
return ignore.some(x => x.test(path));
};
}
/**
* "Refreshes" an extension on `require.extensions`.
*
* @param {string} ext
*/
function reorderRequireExtension(ext) {
const old = require.extensions[ext]; // tslint:disable-line
delete require.extensions[ext]; // tslint:disable-line
require.extensions[ext] = old; // tslint:disable-line
}
/**
* Register the extensions to support when importing files.
*/
function registerExtensions(preferTsExts, extensions, register, originalJsHandler) {
// Register new extensions.
for (const ext of extensions) {
registerExtension(ext, register, originalJsHandler);
}
if (preferTsExts) {
// tslint:disable-next-line
const preferredExtensions = new Set([...extensions, ...Object.keys(require.extensions)]);
for (const ext of preferredExtensions)
reorderRequireExtension(ext);
}
}
/**
* Register the extension for node.
*/
function registerExtension(ext, register, originalHandler) {
const old = require.extensions[ext] || originalHandler; // tslint:disable-line
require.extensions[ext] = function (m, filename) {
if (register.ignored(filename))
return old(m, filename);
const _compile = m._compile;
m._compile = function (code, fileName) {
exports.debug('module._compile', fileName);
return _compile.call(this, register.compile(code, fileName), fileName);
};
return old(m, filename);
};
}
/**
* Do post-processing on config options to support `ts-node`.
*/
function fixConfig(ts, config) {
// Delete options that *should not* be passed through.
delete config.options.out;
delete config.options.outFile;
delete config.options.composite;
delete config.options.declarationDir;
delete config.options.declarationMap;
delete config.options.emitDeclarationOnly;
// Target ES5 output by default (instead of ES3).
if (config.options.target === undefined) {
config.options.target = ts.ScriptTarget.ES5;
}
// Target CommonJS modules by default (instead of magically switching to ES6 when the target is ES6).
if (config.options.module === undefined) {
config.options.module = ts.ModuleKind.CommonJS;
}
return config;
}
/**
* Load TypeScript configuration. Returns the parsed TypeScript config and
* any `ts-node` options specified in the config file.
*/
function readConfig(cwd, ts, rawOptions) {
var _a, _b;
let config = { compilerOptions: {} };
let basePath = cwd;
let configFileName = undefined;
const { fileExists = ts.sys.fileExists, readFile = ts.sys.readFile, skipProject = exports.DEFAULTS.skipProject, project = exports.DEFAULTS.project } = rawOptions;
// Read project configuration when available.
if (!skipProject) {
configFileName = project
? path_1.resolve(cwd, project)
: ts.findConfigFile(cwd, fileExists);
if (configFileName) {
const result = ts.readConfigFile(configFileName, readFile);
// Return diagnostics.
if (result.error) {
return {
config: { errors: [result.error], fileNames: [], options: {} },
options: {}
};
}
config = result.config;
basePath = path_1.dirname(configFileName);
}
}
// Fix ts-node options that come from tsconfig.json
const tsconfigOptions = Object.assign({}, config['ts-node']);
// Remove resolution of "files".
const files = (_b = (_a = rawOptions.files) !== null && _a !== void 0 ? _a : tsconfigOptions.files) !== null && _b !== void 0 ? _b : exports.DEFAULTS.files;
if (!files) {
config.files = [];
config.include = [];
}
// Override default configuration options `ts-node` requires.
config.compilerOptions = Object.assign({}, config.compilerOptions, exports.DEFAULTS.compilerOptions, tsconfigOptions.compilerOptions, rawOptions.compilerOptions, TS_NODE_COMPILER_OPTIONS);
const fixedConfig = fixConfig(ts, ts.parseJsonConfigFileContent(config, {
fileExists,
readFile,
readDirectory: ts.sys.readDirectory,
useCaseSensitiveFileNames: ts.sys.useCaseSensitiveFileNames
}, basePath, undefined, configFileName));
return { config: fixedConfig, options: tsconfigOptions };
}
/**
* Update the output remapping the source map.
*/
function updateOutput(outputText, fileName, sourceMap, getExtension) {
const base64Map = Buffer.from(updateSourceMap(sourceMap, fileName), 'utf8').toString('base64');
const sourceMapContent = `data:application/json;charset=utf-8;base64,${base64Map}`;
const sourceMapLength = `${path_1.basename(fileName)}.map`.length + (getExtension(fileName).length - path_1.extname(fileName).length);
return outputText.slice(0, -sourceMapLength) + sourceMapContent;
}
/**
* Update the source map contents for improved output.
*/
function updateSourceMap(sourceMapText, fileName) {
const sourceMap = JSON.parse(sourceMapText);
sourceMap.file = fileName;
sourceMap.sources = [fileName];
delete sourceMap.sourceRoot;
return JSON.stringify(sourceMap);
}
/**
* Filter diagnostics.
*/
function filterDiagnostics(diagnostics, ignore) {
return diagnostics.filter(x => ignore.indexOf(x.code) === -1);
}
/**
* Get token at file position.
*
* Reference: https://github.com/microsoft/TypeScript/blob/fcd9334f57d85b73dd66ad2d21c02e84822f4841/src/services/utilities.ts#L705-L731
*/
function getTokenAtPosition(ts, sourceFile, position) {
let current = sourceFile;
outer: while (true) {
for (const child of current.getChildren(sourceFile)) {
const start = child.getFullStart();
if (start > position)
break;
const end = child.getEnd();
if (position <= end) {
current = child;
continue outer;
}
}
return current;
}
}
//# sourceMappingURL=index.js.map
-1
View File
File diff suppressed because one or more lines are too long
-1
View File
@@ -1 +0,0 @@
export {};
-553
View File
@@ -1,553 +0,0 @@
"use strict";
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
Object.defineProperty(exports, "__esModule", { value: true });
const chai_1 = require("chai");
const child_process_1 = require("child_process");
const path_1 = require("path");
const semver = require("semver");
const ts = require("typescript");
const proxyquire = require("proxyquire");
const index_1 = require("./index");
const fs_1 = require("fs");
const promisify = require("util.promisify");
const execP = promisify(child_process_1.exec);
const TEST_DIR = path_1.join(__dirname, '../tests');
const PROJECT = path_1.join(TEST_DIR, 'tsconfig.json');
const BIN_PATH = path_1.join(TEST_DIR, 'node_modules/.bin/ts-node');
const BIN_SCRIPT_PATH = path_1.join(TEST_DIR, 'node_modules/.bin/ts-node-script');
const SOURCE_MAP_REGEXP = /\/\/# sourceMappingURL=data:application\/json;charset=utf\-8;base64,[\w\+]+=*$/;
// Pack and install ts-node locally, necessary to test package "exports"
before(function () {
return __awaiter(this, void 0, void 0, function* () {
this.timeout(30000);
yield execP(`npm install`, { cwd: TEST_DIR });
const packageLockPath = path_1.join(TEST_DIR, 'package-lock.json');
fs_1.existsSync(packageLockPath) && fs_1.unlinkSync(packageLockPath);
});
});
describe('ts-node', function () {
const cmd = `"${BIN_PATH}" --project "${PROJECT}"`;
this.timeout(10000);
it('should export the correct version', function () {
chai_1.expect(index_1.VERSION).to.equal(require('../package.json').version);
});
describe('cli', function () {
this.slow(1000);
it('should execute cli', function (done) {
child_process_1.exec(`${cmd} tests/hello-world`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('Hello, world!\n');
return done();
});
});
it('should register via cli', function (done) {
child_process_1.exec(`node -r ts-node/register hello-world.ts`, {
cwd: TEST_DIR
}, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('Hello, world!\n');
return done();
});
});
it('should execute cli with absolute path', function (done) {
child_process_1.exec(`${cmd} "${path_1.join(TEST_DIR, 'hello-world')}"`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('Hello, world!\n');
return done();
});
});
it('should print scripts', function (done) {
child_process_1.exec(`${cmd} -pe "import { example } from './tests/complex/index';example()"`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('example\n');
return done();
});
});
it('should provide registered information globally', function (done) {
child_process_1.exec(`${cmd} tests/env`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('object\n');
return done();
});
});
it('should provide registered information on register', function (done) {
child_process_1.exec(`node -r ts-node/register env.ts`, {
cwd: TEST_DIR
}, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('object\n');
return done();
});
});
if (semver.gte(ts.version, '1.8.0')) {
it('should allow js', function (done) {
child_process_1.exec([
cmd,
'-O "{\\\"allowJs\\\":true}"',
'-pe "import { main } from \'./tests/allow-js/run\';main()"'
].join(' '), function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('hello world\n');
return done();
});
});
it('should include jsx when `allow-js` true', function (done) {
child_process_1.exec([
cmd,
'-O "{\\\"allowJs\\\":true}"',
'-pe "import { Foo2 } from \'./tests/allow-js/with-jsx\'; Foo2.sayHi()"'
].join(' '), function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('hello world\n');
return done();
});
});
}
it('should eval code', function (done) {
child_process_1.exec(`${cmd} -e "import * as m from './tests/module';console.log(m.example('test'))"`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('TEST\n');
return done();
});
});
it('should import empty files', function (done) {
child_process_1.exec(`${cmd} -e "import './tests/empty'"`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('');
return done();
});
});
it('should throw errors', function (done) {
child_process_1.exec(`${cmd} -e "import * as m from './tests/module';console.log(m.example(123))"`, function (err) {
if (err === null) {
return done('Command was expected to fail, but it succeeded.');
}
chai_1.expect(err.message).to.match(new RegExp('TS2345: Argument of type \'(?:number|123)\' ' +
'is not assignable to parameter of type \'string\'\\.'));
return done();
});
});
it('should be able to ignore diagnostic', function (done) {
child_process_1.exec(`${cmd} --ignore-diagnostics 2345 -e "import * as m from './tests/module';console.log(m.example(123))"`, function (err) {
if (err === null) {
return done('Command was expected to fail, but it succeeded.');
}
chai_1.expect(err.message).to.match(/TypeError: (?:(?:undefined|foo\.toUpperCase) is not a function|.*has no method \'toUpperCase\')/);
return done();
});
});
it('should work with source maps', function (done) {
child_process_1.exec(`${cmd} tests/throw`, function (err) {
if (err === null) {
return done('Command was expected to fail, but it succeeded.');
}
chai_1.expect(err.message).to.contain([
`${path_1.join(__dirname, '../tests/throw.ts')}:100`,
' bar () { throw new Error(\'this is a demo\') }',
' ^',
'Error: this is a demo'
].join('\n'));
return done();
});
});
it('eval should work with source maps', function (done) {
child_process_1.exec(`${cmd} -pe "import './tests/throw'"`, function (err) {
if (err === null) {
return done('Command was expected to fail, but it succeeded.');
}
chai_1.expect(err.message).to.contain([
`${path_1.join(__dirname, '../tests/throw.ts')}:100`,
' bar () { throw new Error(\'this is a demo\') }',
' ^'
].join('\n'));
return done();
});
});
it('should support transpile only mode', function (done) {
child_process_1.exec(`${cmd} --transpile-only -pe "x"`, function (err) {
if (err === null) {
return done('Command was expected to fail, but it succeeded.');
}
chai_1.expect(err.message).to.contain('ReferenceError: x is not defined');
return done();
});
});
it('should throw error even in transpileOnly mode', function (done) {
child_process_1.exec(`${cmd} --transpile-only -pe "console."`, function (err) {
if (err === null) {
return done('Command was expected to fail, but it succeeded.');
}
chai_1.expect(err.message).to.contain('error TS1003: Identifier expected');
return done();
});
});
it('should pipe into `ts-node` and evaluate', function (done) {
const cp = child_process_1.exec(cmd, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('hello\n');
return done();
});
cp.stdin.end("console.log('hello')");
});
it('should pipe into `ts-node`', function (done) {
const cp = child_process_1.exec(`${cmd} -p`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('true\n');
return done();
});
cp.stdin.end('true');
});
it('should pipe into an eval script', function (done) {
const cp = child_process_1.exec(`${cmd} --transpile-only -pe "process.stdin.isTTY"`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('undefined\n');
return done();
});
cp.stdin.end('true');
});
it('should run REPL when --interactive passed and stdin is not a TTY', function (done) {
const cp = child_process_1.exec(`${cmd} --interactive`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('> 123\n' +
'undefined\n' +
'> ');
return done();
});
cp.stdin.end('console.log("123")\n');
});
it('should support require flags', function (done) {
child_process_1.exec(`${cmd} -r ./tests/hello-world -pe "console.log('success')"`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('Hello, world!\nsuccess\nundefined\n');
return done();
});
});
it('should support require from node modules', function (done) {
child_process_1.exec(`${cmd} -r typescript -e "console.log('success')"`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('success\n');
return done();
});
});
it.skip('should use source maps with react tsx', function (done) {
child_process_1.exec(`${cmd} -r ./tests/emit-compiled.ts tests/jsx-react.tsx`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('todo');
return done();
});
});
it('should allow custom typings', function (done) {
child_process_1.exec(`${cmd} tests/custom-types`, function (err, stdout) {
chai_1.expect(err).to.match(/Error: Cannot find module 'does-not-exist'/);
return done();
});
});
it('should preserve `ts-node` context with child process', function (done) {
child_process_1.exec(`${cmd} tests/child-process`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('Hello, world!\n');
return done();
});
});
it('should import js before ts by default', function (done) {
child_process_1.exec(`${cmd} tests/import-order/compiled`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('Hello, JavaScript!\n');
return done();
});
});
it('should import ts before js when --prefer-ts-exts flag is present', function (done) {
child_process_1.exec(`${cmd} --prefer-ts-exts tests/import-order/compiled`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('Hello, TypeScript!\n');
return done();
});
});
it('should import ts before js when TS_NODE_PREFER_TS_EXTS env is present', function (done) {
child_process_1.exec(`${cmd} tests/import-order/compiled`, { env: Object.assign(Object.assign({}, process.env), { TS_NODE_PREFER_TS_EXTS: 'true' }) }, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('Hello, TypeScript!\n');
return done();
});
});
it('should ignore .d.ts files', function (done) {
child_process_1.exec(`${cmd} tests/import-order/importer`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('Hello, World!\n');
return done();
});
});
describe('issue #884', function () {
it('should compile', function (done) {
// TODO disabled because it consistently fails on Windows on TS 2.7
if (process.platform === 'win32' && semver.satisfies(ts.version, '2.7')) {
this.skip();
}
else {
child_process_1.exec(`"${BIN_PATH}" --project tests/issue-884/tsconfig.json tests/issue-884`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('');
return done();
});
}
});
});
describe('issue #986', function () {
it('should not compile', function (done) {
child_process_1.exec(`"${BIN_PATH}" --project tests/issue-986/tsconfig.json tests/issue-986`, function (err, stdout, stderr) {
chai_1.expect(err).not.to.equal(null);
chai_1.expect(stderr).to.contain('Cannot find name \'TEST\''); // TypeScript error.
chai_1.expect(stdout).to.equal('');
return done();
});
});
it('should compile with `--files`', function (done) {
child_process_1.exec(`"${BIN_PATH}" --files --project tests/issue-986/tsconfig.json tests/issue-986`, function (err, stdout, stderr) {
chai_1.expect(err).not.to.equal(null);
chai_1.expect(stderr).to.contain('ReferenceError: TEST is not defined'); // Runtime error.
chai_1.expect(stdout).to.equal('');
return done();
});
});
});
if (semver.gte(ts.version, '2.7.0')) {
it('should support script mode', function (done) {
child_process_1.exec(`${BIN_SCRIPT_PATH} tests/scope/a/log`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('.ts\n');
return done();
});
});
it('should read tsconfig relative to realpath, not symlink, in scriptMode', function (done) {
if (fs_1.statSync(path_1.join(TEST_DIR, 'main-realpath/symlink/symlink.tsx')).isSymbolicLink()) {
child_process_1.exec(`${BIN_SCRIPT_PATH} tests/main-realpath/symlink/symlink.tsx`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('');
return done();
});
}
else {
this.skip();
}
});
}
describe('should read ts-node options from tsconfig.json', function () {
const BIN_EXEC = `"${BIN_PATH}" --project tests/tsconfig-options/tsconfig.json`;
it('should override compiler options from env', function (done) {
child_process_1.exec(`${BIN_EXEC} tests/tsconfig-options/log-options.js`, {
env: Object.assign(Object.assign({}, process.env), { TS_NODE_COMPILER_OPTIONS: '{"typeRoots": ["env-typeroots"]}' })
}, function (err, stdout) {
chai_1.expect(err).to.equal(null);
const { config } = JSON.parse(stdout);
chai_1.expect(config.options.typeRoots).to.deep.equal([path_1.join(__dirname, '../tests/tsconfig-options/env-typeroots').replace(/\\/g, '/')]);
return done();
});
});
it('should use options from `tsconfig.json`', function (done) {
child_process_1.exec(`${BIN_EXEC} tests/tsconfig-options/log-options.js`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
const { options, config } = JSON.parse(stdout);
chai_1.expect(config.options.typeRoots).to.deep.equal([path_1.join(__dirname, '../tests/tsconfig-options/tsconfig-typeroots').replace(/\\/g, '/')]);
chai_1.expect(config.options.types).to.deep.equal(['tsconfig-tsnode-types']);
chai_1.expect(options.pretty).to.equal(undefined);
chai_1.expect(options.skipIgnore).to.equal(false);
chai_1.expect(options.transpileOnly).to.equal(true);
return done();
});
});
it('should have flags override `tsconfig.json`', function (done) {
child_process_1.exec(`${BIN_EXEC} --skip-ignore --compiler-options "{\\"types\\":[\\"flags-types\\"]}" tests/tsconfig-options/log-options.js`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
const { options, config } = JSON.parse(stdout);
chai_1.expect(config.options.typeRoots).to.deep.equal([path_1.join(__dirname, '../tests/tsconfig-options/tsconfig-typeroots').replace(/\\/g, '/')]);
chai_1.expect(config.options.types).to.deep.equal(['flags-types']);
chai_1.expect(options.pretty).to.equal(undefined);
chai_1.expect(options.skipIgnore).to.equal(true);
chai_1.expect(options.transpileOnly).to.equal(true);
return done();
});
});
it('should have `tsconfig.json` override environment', function (done) {
child_process_1.exec(`${BIN_EXEC} tests/tsconfig-options/log-options.js`, {
env: Object.assign(Object.assign({}, process.env), { TS_NODE_PRETTY: 'true', TS_NODE_SKIP_IGNORE: 'true' })
}, function (err, stdout) {
chai_1.expect(err).to.equal(null);
const { options, config } = JSON.parse(stdout);
chai_1.expect(config.options.typeRoots).to.deep.equal([path_1.join(__dirname, '../tests/tsconfig-options/tsconfig-typeroots').replace(/\\/g, '/')]);
chai_1.expect(config.options.types).to.deep.equal(['tsconfig-tsnode-types']);
chai_1.expect(options.pretty).to.equal(true);
chai_1.expect(options.skipIgnore).to.equal(false);
chai_1.expect(options.transpileOnly).to.equal(true);
return done();
});
});
});
describe('compiler host', function () {
it('should execute cli', function (done) {
child_process_1.exec(`${cmd} --compiler-host tests/hello-world`, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('Hello, world!\n');
return done();
});
});
it('should give ts error for invalid node_modules', function (done) {
child_process_1.exec(`${cmd} --compiler-host --skip-ignore tests/from-node-modules/from-node-modules`, function (err, stdout) {
if (err === null)
return done('Expected an error');
chai_1.expect(err.message).to.contain('Unable to compile file from external library');
return done();
});
});
});
});
describe('register', function () {
const registered = index_1.register({
project: PROJECT,
compilerOptions: {
jsx: 'preserve'
}
});
const moduleTestPath = require.resolve('../tests/module');
afterEach(() => {
// Re-enable project after every test.
registered.enabled(true);
});
it('should be able to require typescript', function () {
const m = require(moduleTestPath);
chai_1.expect(m.example('foo')).to.equal('FOO');
});
it('should support dynamically disabling', function () {
delete require.cache[moduleTestPath];
chai_1.expect(registered.enabled(false)).to.equal(false);
chai_1.expect(() => require(moduleTestPath)).to.throw(/Unexpected token/);
delete require.cache[moduleTestPath];
chai_1.expect(registered.enabled()).to.equal(false);
chai_1.expect(() => require(moduleTestPath)).to.throw(/Unexpected token/);
delete require.cache[moduleTestPath];
chai_1.expect(registered.enabled(true)).to.equal(true);
chai_1.expect(() => require(moduleTestPath)).to.not.throw();
delete require.cache[moduleTestPath];
chai_1.expect(registered.enabled()).to.equal(true);
chai_1.expect(() => require(moduleTestPath)).to.not.throw();
});
if (semver.gte(ts.version, '2.7.0')) {
it('should support compiler scopes', function () {
const calls = [];
registered.enabled(false);
const compilers = [
index_1.register({ dir: path_1.join(TEST_DIR, 'scope/a'), scope: true }),
index_1.register({ dir: path_1.join(TEST_DIR, 'scope/b'), scope: true })
];
compilers.forEach(c => {
const old = c.compile;
c.compile = (code, fileName, lineOffset) => {
calls.push(fileName);
return old(code, fileName, lineOffset);
};
});
try {
chai_1.expect(require('../tests/scope/a').ext).to.equal('.ts');
chai_1.expect(require('../tests/scope/b').ext).to.equal('.ts');
}
finally {
compilers.forEach(c => c.enabled(false));
}
chai_1.expect(calls).to.deep.equal([
path_1.join(TEST_DIR, 'scope/a/index.ts'),
path_1.join(TEST_DIR, 'scope/b/index.ts')
]);
delete require.cache[moduleTestPath];
chai_1.expect(() => require(moduleTestPath)).to.throw();
});
}
it('should compile through js and ts', function () {
const m = require('../tests/complex');
chai_1.expect(m.example()).to.equal('example');
});
it('should work with proxyquire', function () {
const m = proxyquire('../tests/complex', {
'./example': 'hello'
});
chai_1.expect(m.example()).to.equal('hello');
});
it('should work with `require.cache`', function () {
const { example1, example2 } = require('../tests/require-cache');
chai_1.expect(example1).to.not.equal(example2);
});
it('should use source maps', function (done) {
try {
require('../tests/throw');
}
catch (error) {
chai_1.expect(error.stack).to.contain([
'Error: this is a demo',
` at Foo.bar (${path_1.join(__dirname, '../tests/throw.ts')}:100:18)`
].join('\n'));
done();
}
});
describe('JSX preserve', () => {
let old = require.extensions['.tsx']; // tslint:disable-line
let compiled;
before(function () {
require.extensions['.tsx'] = (m, fileName) => {
const _compile = m._compile;
m._compile = (code, fileName) => {
compiled = code;
return _compile.call(this, code, fileName);
};
return old(m, fileName);
};
});
after(function () {
require.extensions['.tsx'] = old; // tslint:disable-line
});
it('should use source maps', function (done) {
try {
require('../tests/with-jsx.tsx');
}
catch (error) {
chai_1.expect(error.stack).to.contain('SyntaxError: Unexpected token');
}
chai_1.expect(compiled).to.match(SOURCE_MAP_REGEXP);
done();
});
});
});
describe('create', () => {
it('should create generic compiler instances', () => {
const service = index_1.create({ compilerOptions: { target: 'es5' }, skipProject: true });
const output = service.compile('const x = 10', 'test.ts');
chai_1.expect(output).to.contain('var x = 10;');
});
});
if (semver.gte(process.version, '13.0.0')) {
describe('esm', () => {
this.slow(1000);
const cmd = `node --loader ../../esm.mjs`;
it('should compile and execute as ESM', (done) => {
child_process_1.exec(`${cmd} index.ts`, { cwd: path_1.join(__dirname, '../tests/esm') }, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('foo bar baz biff\n');
return done();
});
});
it('supports --experimental-specifier-resolution=node', (done) => {
child_process_1.exec(`${cmd} --experimental-specifier-resolution=node index.ts`, { cwd: path_1.join(__dirname, '../tests/esm-node-resolver') }, function (err, stdout) {
chai_1.expect(err).to.equal(null);
chai_1.expect(stdout).to.equal('foo bar baz biff\n');
return done();
});
});
});
}
});
//# sourceMappingURL=index.spec.js.map
-1
View File
File diff suppressed because one or more lines are too long
-13
View File
@@ -1,13 +0,0 @@
import { TsConfigOptions } from '.';
/**
* tsconfig schema which includes "ts-node" options.
* @allOf [{"$ref": "https://schemastore.azurewebsites.net/schemas/json/tsconfig.json"}]
*/
export interface TsConfigSchema {
/**
* ts-node options. See also: https://github.com/TypeStrong/ts-node#configuration-options
*
* ts-node offers TypeScript execution and REPL for node.js, with source map support.
*/
'ts-node': TsConfigOptions;
}
-3
View File
@@ -1,3 +0,0 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
//# sourceMappingURL=tsconfig-schema.js.map
-1
View File
@@ -1 +0,0 @@
{"version":3,"file":"tsconfig-schema.js","sourceRoot":"","sources":["../src/tsconfig-schema.ts"],"names":[],"mappings":"","sourcesContent":["import { TsConfigOptions } from '.'\n\n/*\n * This interface exists solely for generating a JSON schema for tsconfig.json.\n * We do *not* extend the compiler's tsconfig interface. Instead we handle that\n * on a schema level, via \"allOf\", so we pull in the same schema that VSCode\n * already uses.\n */\n/**\n * tsconfig schema which includes \"ts-node\" options.\n * @allOf [{\"$ref\": \"https://schemastore.azurewebsites.net/schemas/json/tsconfig.json\"}]\n */\nexport interface TsConfigSchema {\n /**\n * ts-node options. See also: https://github.com/TypeStrong/ts-node#configuration-options\n *\n * ts-node offers TypeScript execution and REPL for node.js, with source map support.\n */\n 'ts-node': TsConfigOptions\n}\n"]}
-7
View File
@@ -1,7 +0,0 @@
import {fileURLToPath} from 'url'
import {createRequire} from 'module'
const require = createRequire(fileURLToPath(import.meta.url))
/** @type {import('./dist/esm')} */
const esm = require('./dist/esm')
export const {resolve, getFormat, transformSource} = esm.registerAndCreateEsmHooks()
-123
View File
@@ -1,123 +0,0 @@
{
"_args": [
[
"ts-node@8.10.2",
"/mnt/Foxconn/Digitalent/Deverloper/liff-push_2series"
]
],
"_from": "ts-node@8.10.2",
"_id": "ts-node@8.10.2",
"_inBundle": false,
"_integrity": "sha512-ISJJGgkIpDdBhWVu3jufsWpK3Rzo7bdiIXJjQc0ynKxVOVcg2oIrf2H2cejminGrptVc6q6/uynAHNCuWGbpVA==",
"_location": "/ts-node",
"_phantomChildren": {},
"_requested": {
"type": "version",
"registry": true,
"raw": "ts-node@8.10.2",
"name": "ts-node",
"escapedName": "ts-node",
"rawSpec": "8.10.2",
"saveSpec": null,
"fetchSpec": "8.10.2"
},
"_requiredBy": [
"/@nuxt/typescript-runtime"
],
"_resolved": "https://registry.npmjs.org/ts-node/-/ts-node-8.10.2.tgz",
"_spec": "8.10.2",
"_where": "/mnt/Foxconn/Digitalent/Deverloper/liff-push_2series",
"author": {
"name": "Blake Embrey",
"email": "hello@blakeembrey.com",
"url": "http://blakeembrey.me"
},
"bin": {
"ts-node": "dist/bin.js",
"ts-script": "dist/bin-script-deprecated.js",
"ts-node-script": "dist/bin-script.js",
"ts-node-transpile-only": "dist/bin-transpile.js"
},
"bugs": {
"url": "https://github.com/TypeStrong/ts-node/issues"
},
"dependencies": {
"arg": "^4.1.0",
"diff": "^4.0.1",
"make-error": "^1.1.1",
"source-map-support": "^0.5.17",
"yn": "3.1.1"
},
"description": "TypeScript execution environment and REPL for node.js, with source map support",
"devDependencies": {
"@types/chai": "^4.0.4",
"@types/diff": "^4.0.2",
"@types/mocha": "^5.2.7",
"@types/node": "13.13.5",
"@types/proxyquire": "^1.3.28",
"@types/react": "^16.0.2",
"@types/semver": "^7.1.0",
"@types/source-map-support": "^0.5.0",
"axios": "^0.19.0",
"chai": "^4.0.1",
"istanbul": "^0.4.0",
"mocha": "^6.2.2",
"ntypescript": "^1.201507091536.1",
"proxyquire": "^2.0.0",
"react": "^16.0.0",
"rimraf": "^3.0.0",
"semver": "^7.1.3",
"tslint": "^6.1.0",
"tslint-config-standard": "^9.0.0",
"typescript": "3.8.3",
"typescript-json-schema": "^0.42.0",
"util.promisify": "^1.0.1"
},
"engines": {
"node": ">=6.0.0"
},
"files": [
"dist/",
"dist-raw/",
"register/",
"esm.mjs",
"LICENSE",
"tsconfig.schema.json",
"tsconfig.schemastore-schema.json"
],
"homepage": "https://github.com/TypeStrong/ts-node",
"keywords": [
"typescript",
"node",
"runtime",
"environment",
"ts",
"compiler"
],
"license": "MIT",
"main": "dist/index.js",
"name": "ts-node",
"peerDependencies": {
"typescript": ">=2.7"
},
"repository": {
"type": "git",
"url": "git://github.com/TypeStrong/ts-node.git"
},
"scripts": {
"build": "npm run build-nopack && npm run build-pack",
"build-configSchema": "typescript-json-schema --topRef --refs --validationKeywords allOf --out tsconfig.schema.json tsconfig.json TsConfigSchema && node --require ./register ./scripts/create-merged-schema",
"build-nopack": "npm run clean && npm run build-tsc && npm run build-configSchema",
"build-pack": "node ./scripts/build-pack.js",
"build-tsc": "tsc",
"clean": "rimraf dist && rimraf tsconfig.schema.json && rimraf tsconfig.schemastore-schema.json && rimraf tests/ts-node-packed.tgz",
"lint": "tslint \"src/**/*.ts\" --project tsconfig.json",
"lint-fix": "tslint \"src/**/*.ts\" --project tsconfig.json --fix",
"prepare": "npm run build-nopack",
"test": "npm run build && npm run lint && npm run test-cov",
"test-cov": "istanbul cover node_modules/mocha/bin/_mocha -- \"dist/**/*.spec.js\" -R spec --bail",
"test-spec": "mocha dist/**/*.spec.js -R spec --bail"
},
"types": "dist/index.d.ts",
"version": "8.10.2"
}
-3
View File
@@ -1,3 +0,0 @@
require('../dist').register({
files: true
})
-1
View File
@@ -1 +0,0 @@
require('../').register()
-3
View File
@@ -1,3 +0,0 @@
require('../').register({
transpileOnly: true
})
-3
View File
@@ -1,3 +0,0 @@
require('../').register({
typeCheck: true
})
-113
View File
@@ -1,113 +0,0 @@
{
"$ref": "#/definitions/TsConfigSchema",
"$schema": "http://json-schema.org/draft-07/schema#",
"definitions": {
"TsConfigOptions": {
"description": "Must be an interface to support `typescript-json-schema`.",
"properties": {
"compiler": {
"default": "typescript",
"description": "Specify a custom TypeScript compiler.",
"type": "string"
},
"compilerHost": {
"default": false,
"description": "Use TypeScript's compiler host API.",
"type": "boolean"
},
"compilerOptions": {
"additionalProperties": true,
"allOf": [
{
"$ref": "https://schemastore.azurewebsites.net/schemas/json/tsconfig.json#definitions/compilerOptionsDefinition/properties/compilerOptions"
}
],
"description": "JSON object to merge with compiler options.",
"properties": {
},
"type": "object"
},
"emit": {
"default": false,
"description": "Emit output files into `.ts-node` directory.",
"type": "boolean"
},
"files": {
"default": false,
"description": "Load files from `tsconfig.json` on startup.",
"type": "boolean"
},
"ignore": {
"default": "/node_modules/",
"description": "Override the path patterns to skip compilation.",
"items": {
"type": "string"
},
"type": "array"
},
"ignoreDiagnostics": {
"description": "Ignore TypeScript warnings by diagnostic code.",
"items": {
"type": [
"string",
"number"
]
},
"type": "array"
},
"logError": {
"default": false,
"description": "Logs TypeScript errors to stderr instead of throwing exceptions.",
"type": "boolean"
},
"preferTsExts": {
"default": false,
"description": "Re-order file extensions so that TypeScript imports are preferred.",
"type": "boolean"
},
"pretty": {
"default": false,
"description": "Use pretty diagnostic formatter.",
"type": "boolean"
},
"scope": {
"default": false,
"description": "Scope compiler to files within `cwd`.",
"type": "boolean"
},
"skipIgnore": {
"default": false,
"description": "Skip ignore check.",
"type": "boolean"
},
"transpileOnly": {
"default": false,
"description": "Use TypeScript's faster `transpileModule`.",
"type": "boolean"
},
"typeCheck": {
"default": true,
"description": "**DEPRECATED** Specify type-check is enabled (e.g. `transpileOnly == false`).",
"type": "boolean"
}
},
"type": "object"
},
"TsConfigSchema": {
"allOf": [
{
"$ref": "https://schemastore.azurewebsites.net/schemas/json/tsconfig.json"
}
],
"description": "tsconfig schema which includes \"ts-node\" options.",
"properties": {
"ts-node": {
"$ref": "#/definitions/TsConfigOptions",
"description": "ts-node options. See also: https://github.com/TypeStrong/ts-node#configuration-options\n\nts-node offers TypeScript execution and REPL for node.js, with source map support."
}
},
"type": "object"
}
}
}
-777
View File
@@ -1,777 +0,0 @@
{
"title": "JSON schema for the TypeScript compiler's configuration file",
"$schema": "http://json-schema.org/draft-04/schema#",
"definitions": {
"filesDefinition": {
"properties": {
"files": {
"description": "If no 'files' or 'include' property is present in a tsconfig.json, the compiler defaults to including all files in the containing directory and subdirectories except those specified by 'exclude'. When a 'files' property is specified, only those files and those specified by 'include' are included.",
"type": "array",
"items": {
"type": "string"
}
}
}
},
"excludeDefinition": {
"properties": {
"exclude": {
"description": "Specifies a list of files to be excluded from compilation. The 'exclude' property only affects the files included via the 'include' property and not the 'files' property. Glob patterns require TypeScript version 2.0 or later.",
"type": "array",
"items": {
"type": "string"
}
}
}
},
"includeDefinition": {
"properties": {
"include": {
"description": "Specifies a list of glob patterns that match files to be included in compilation. If no 'files' or 'include' property is present in a tsconfig.json, the compiler defaults to including all files in the containing directory and subdirectories except those specified by 'exclude'. Requires TypeScript version 2.0 or later.",
"type": "array",
"items": {
"type": "string"
}
}
}
},
"compileOnSaveDefinition": {
"properties": {
"compileOnSave": {
"description": "Enable Compile-on-Save for this project.",
"type": "boolean"
}
}
},
"extendsDefinition": {
"properties": {
"extends": {
"description": "Path to base configuration file to inherit from. Requires TypeScript version 2.1 or later.",
"type": "string"
}
}
},
"compilerOptionsDefinition": {
"properties": {
"compilerOptions": {
"type": "object",
"description": "Instructs the TypeScript compiler how to compile .ts files.",
"properties": {
"charset": {
"description": "The character set of the input files.",
"type": "string"
},
"composite": {
"description": "Enables building for project references.",
"type": "boolean"
},
"declaration": {
"description": "Generates corresponding d.ts files.",
"type": "boolean"
},
"declarationDir": {
"description": "Specify output directory for generated declaration files. Requires TypeScript version 2.0 or later.",
"type": [
"string",
"null"
]
},
"diagnostics": {
"description": "Show diagnostic information.",
"type": "boolean"
},
"emitBOM": {
"description": "Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files.",
"type": "boolean"
},
"emitDeclarationOnly": {
"description": "Only emit '.d.ts' declaration files.",
"type": "boolean"
},
"incremental": {
"description": "Enable incremental compilation.",
"type": "boolean"
},
"tsBuildInfoFile": {
"description": "Specify file to store incremental compilation information.",
"type": "string"
},
"inlineSourceMap": {
"description": "Emit a single file with source maps instead of having a separate file.",
"type": "boolean"
},
"inlineSources": {
"description": "Emit the source alongside the sourcemaps within a single file; requires --inlineSourceMap to be set.",
"type": "boolean"
},
"jsx": {
"description": "Specify JSX code generation: 'preserve', 'react', or 'react-native'.",
"enum": [
"preserve",
"react",
"react-native"
]
},
"reactNamespace": {
"description": "Specifies the object invoked for createElement and __spread when targeting 'react' JSX emit.",
"type": "string"
},
"listFiles": {
"description": "Print names of files part of the compilation.",
"type": "boolean"
},
"mapRoot": {
"description": "Specifies the location where debugger should locate map files instead of generated locations",
"type": "string"
},
"module": {
"description": "Specify module code generation: 'None', 'CommonJS', 'AMD', 'System', 'UMD', 'ES6', 'ES2015', 'ES2020' or 'ESNext'. Only 'AMD' and 'System' can be used in conjunction with --outFile.",
"type": "string",
"anyOf": [
{
"enum": [
"CommonJS",
"AMD",
"System",
"UMD",
"ES6",
"ES2015",
"ES2020",
"ESNext",
"None"
]
},
{
"pattern": "^([Cc][Oo][Mm][Mm][Oo][Nn][Jj][Ss]|[AaUu][Mm][Dd]|[Ss][Yy][Ss][Tt][Ee][Mm]|[Ee][Ss]([356]|201[567]|2020|[Nn][Ee][Xx][Tt])|[Nn][Oo][Nn][Ee])$"
}
]
},
"newLine": {
"description": "Specifies the end of line sequence to be used when emitting files: 'crlf' (Windows) or 'lf' (Unix).",
"type": "string",
"anyOf": [
{
"enum": [
"crlf",
"lf"
]
},
{
"pattern": "^(CRLF|LF|crlf|lf)$"
}
]
},
"noEmit": {
"description": "Do not emit output.",
"type": "boolean"
},
"noEmitHelpers": {
"description": "Do not generate custom helper functions like __extends in compiled output.",
"type": "boolean"
},
"noEmitOnError": {
"description": "Do not emit outputs if any type checking errors were reported.",
"type": "boolean"
},
"noImplicitAny": {
"description": "Warn on expressions and declarations with an implied 'any' type.",
"type": "boolean"
},
"noImplicitThis": {
"description": "Raise error on 'this' expressions with an implied any type.",
"type": "boolean"
},
"noUnusedLocals": {
"description": "Report errors on unused locals. Requires TypeScript version 2.0 or later.",
"type": "boolean"
},
"noUnusedParameters": {
"description": "Report errors on unused parameters. Requires TypeScript version 2.0 or later.",
"type": "boolean"
},
"noLib": {
"description": "Do not include the default library file (lib.d.ts).",
"type": "boolean"
},
"noResolve": {
"description": "Do not add triple-slash references or module import targets to the list of compiled files.",
"type": "boolean"
},
"noStrictGenericChecks": {
"description": "Disable strict checking of generic signatures in function types.",
"type": "boolean"
},
"skipDefaultLibCheck": {
"type": "boolean"
},
"skipLibCheck": {
"description": "Skip type checking of declaration files. Requires TypeScript version 2.0 or later.",
"type": "boolean"
},
"outFile": {
"description": "Concatenate and emit output to single file.",
"type": "string"
},
"outDir": {
"description": "Redirect output structure to the directory.",
"type": "string"
},
"preserveConstEnums": {
"description": "Do not erase const enum declarations in generated code.",
"type": "boolean"
},
"preserveSymlinks": {
"description": "Do not resolve symlinks to their real path; treat a symlinked file like a real one.",
"type": "boolean"
},
"preserveWatchOutput": {
"description": "Keep outdated console output in watch mode instead of clearing the screen.",
"type": "boolean"
},
"pretty": {
"description": "Stylize errors and messages using color and context (experimental).",
"type": "boolean"
},
"removeComments": {
"description": "Do not emit comments to output.",
"type": "boolean"
},
"rootDir": {
"description": "Specifies the root directory of input files. Use to control the output directory structure with --outDir.",
"type": "string"
},
"isolatedModules": {
"description": "Unconditionally emit imports for unresolved files.",
"type": "boolean"
},
"sourceMap": {
"description": "Generates corresponding '.map' file.",
"type": "boolean"
},
"sourceRoot": {
"description": "Specifies the location where debugger should locate TypeScript files instead of source locations.",
"type": "string"
},
"suppressExcessPropertyErrors": {
"description": "Suppress excess property checks for object literals.",
"type": "boolean"
},
"suppressImplicitAnyIndexErrors": {
"description": "Suppress noImplicitAny errors for indexing objects lacking index signatures.",
"type": "boolean"
},
"stripInternal": {
"description": "Do not emit declarations for code that has an '@internal' annotation.",
"type": "boolean"
},
"target": {
"description": "Specify ECMAScript target version: 'ES3', 'ES5', 'ES6'/'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019', 'ES2020', 'ESNext'",
"type": "string",
"default": "ES3",
"anyOf": [
{
"enum": [
"ES3",
"ES5",
"ES6",
"ES2015",
"ES2016",
"ES2017",
"ES2018",
"ES2019",
"ES2020",
"ESNext"
]
},
{
"pattern": "^([Ee][Ss]([356]|(20(1[56789]|20))|[Nn][Ee][Xx][Tt]))$"
}
]
},
"watch": {
"description": "Watch input files.",
"type": "boolean"
},
"experimentalDecorators": {
"description": "Enables experimental support for ES7 decorators.",
"type": "boolean"
},
"emitDecoratorMetadata": {
"description": "Emit design-type metadata for decorated declarations in source.",
"type": "boolean"
},
"moduleResolution": {
"description": "Specifies module resolution strategy: 'node' (Node) or 'classic' (TypeScript pre 1.6) .",
"type": "string",
"anyOf": [
{
"enum": [
"Classic",
"Node"
]
},
{
"pattern": "^(([Nn]ode)|([Cc]lassic))$"
}
],
"default": "classic"
},
"allowUnusedLabels": {
"type": "boolean",
"description": "Do not report errors on unused labels."
},
"noImplicitReturns": {
"description": "Report error when not all code paths in function return a value.",
"type": "boolean"
},
"noFallthroughCasesInSwitch": {
"description": "Report errors for fallthrough cases in switch statement.",
"type": "boolean"
},
"allowUnreachableCode": {
"description": "Do not report errors on unreachable code.",
"type": "boolean"
},
"forceConsistentCasingInFileNames": {
"description": "Disallow inconsistently-cased references to the same file.",
"type": "boolean"
},
"baseUrl": {
"description": "Base directory to resolve non-relative module names.",
"type": "string"
},
"paths": {
"description": "Specify path mapping to be computed relative to baseUrl option.",
"type": "object",
"additionalProperties": {
"type": "array",
"items": {
"type": "string",
"description": "Path mapping to be computed relative to baseUrl option."
}
}
},
"plugins": {
"description": "List of TypeScript language server plugins to load. Requires TypeScript version 2.3 or later.",
"type": "array",
"items": {
"type": "object",
"properties": {
"name": {
"description": "Plugin name.",
"type": "string"
}
}
}
},
"rootDirs": {
"description": "Specify list of root directories to be used when resolving modules.",
"type": "array",
"items": {
"type": "string"
}
},
"typeRoots": {
"description": "Specify list of directories for type definition files to be included. Requires TypeScript version 2.0 or later.",
"type": "array",
"items": {
"type": "string"
}
},
"types": {
"description": "Type declaration files to be included in compilation. Requires TypeScript version 2.0 or later.",
"type": "array",
"items": {
"type": "string"
}
},
"traceResolution": {
"description": "Enable tracing of the name resolution process.",
"type": "boolean"
},
"allowJs": {
"description": "Allow javascript files to be compiled.",
"type": "boolean"
},
"noErrorTruncation": {
"description": "Do not truncate error messages.",
"type": "boolean"
},
"allowSyntheticDefaultImports": {
"description": "Allow default imports from modules with no default export. This does not affect code emit, just typechecking.",
"type": "boolean"
},
"noImplicitUseStrict": {
"description": "Do not emit 'use strict' directives in module output.",
"type": "boolean"
},
"listEmittedFiles": {
"description": "Enable to list all emitted files. Requires TypeScript version 2.0 or later.",
"type": "boolean"
},
"disableSizeLimit": {
"description": "Disable size limit for JavaScript project. Requires TypeScript version 2.0 or later.",
"type": "boolean",
"default": false
},
"lib": {
"description": "List of library files to be included in the compilation. Possible values are: 'ES5', 'ES6', 'ES2015', 'ES7', 'ES2016', 'ES2017', 'ES2018', 'ESNext', 'DOM', 'DOM.Iterable', 'WebWorker', 'ScriptHost', 'ES2015.Core', 'ES2015.Collection', 'ES2015.Generator', 'ES2015.Iterable', 'ES2015.Promise', 'ES2015.Proxy', 'ES2015.Reflect', 'ES2015.Symbol', 'ES2015.Symbol.WellKnown', 'ES2016.Array.Include', 'ES2017.object', 'ES2017.Intl', 'ES2017.SharedMemory', 'ES2017.String', 'ES2017.TypedArrays', 'ES2018.Intl', 'ES2018.Promise', 'ES2018.RegExp', 'ESNext.AsyncIterable', 'ESNext.Array', 'ESNext.Intl', 'ESNext.Symbol'. Requires TypeScript version 2.0 or later.",
"type": "array",
"items": {
"type": "string",
"anyOf": [
{
"enum": [
"ES5",
"ES6",
"ES7",
"ES2015",
"ES2015.Collection",
"ES2015.Core",
"ES2015.Generator",
"ES2015.Iterable",
"ES2015.Promise",
"ES2015.Proxy",
"ES2015.Reflect",
"ES2015.Symbol.WellKnown",
"ES2015.Symbol",
"ES2016",
"ES2016.Array.Include",
"ES2017",
"ES2017.Intl",
"ES2017.Object",
"ES2017.SharedMemory",
"ES2017.String",
"ES2017.TypedArrays",
"ES2018",
"ES2018.AsyncIterable",
"ES2018.Intl",
"ES2018.Promise",
"ES2018.Regexp",
"ES2019",
"ES2019.Array",
"ES2019.Object",
"ES2019.String",
"ES2019.Symbol",
"ES2020",
"ES2020.BigInt",
"ES2020.Promise",
"ES2020.String",
"ES2020.Symbol.WellKnown",
"ESNext",
"ESNext.Array",
"ESNext.AsyncIterable",
"ESNext.BigInt",
"ESNext.Intl",
"ESNext.Symbol",
"DOM",
"DOM.Iterable",
"ScriptHost",
"WebWorker",
"WebWorker.ImportScripts"
]
},
{
"pattern": "^[Ee][Ss]5|[Ee][Ss]6|[Ee][Ss]7$"
},
{
"pattern": "^[Ee][Ss]2015(\\.([Cc][Oo][Ll][Ll][Ee][Cc][Tt][Ii][Oo][Nn]|[Cc][Oo][Rr][Ee]|[Gg][Ee][Nn][Ee][Rr][Aa][Tt][Oo][Rr]|[Ii][Tt][Ee][Rr][Aa][Bb][Ll][Ee]|[Pp][Rr][Oo][Mm][Ii][Ss][Ee]|[Pp][Rr][Oo][Xx][Yy]|[Rr][Ee][Ff][Ll][Ee][Cc][Tt]|[Ss][Yy][Mm][Bb][Oo][Ll].[Ww][Ee][Ll][Ll][Kk][Nn][Oo][Ww][Nn]|[Ss][Yy][Mm][Bb][Oo][Ll]))?$"
},
{
"pattern": "^[Ee][Ss]2016(\\.[Aa][Rr][Rr][Aa][Yy].[Ii][Nn][Cc][Ll][Uu][Dd][Ee])?$"
},
{
"pattern": "^[Ee][Ss]2017(\\.([Ii][Nn][Tt][Ll]|[Oo][Bb][Jj][Ee][Cc][Tt]|[Ss][Hh][Aa][Rr][Ee][Dd][Mm][Ee][Mm][Oo][Rr][Yy]|[Ss][Tt][Rr][Ii][Nn][Gg]|[Tt][Yy][Pp][Ee][Dd][Aa][Rr][Rr][Aa][Yy][Ss]))?$"
},
{
"pattern": "^[Ee][Ss]2018(\\.([Aa][Ss][Yy][Nn][Cc][Ii][Tt][Ee][Rr][Aa][Bb][Ll][Ee]|[Ii][Nn][Tt][Ll]|[Pp][Rr][Oo][Mm][Ii][Ss][Ee]|[Rr][Ee][Gg][Ee][Xx][Pp]))?$"
},
{
"pattern": "^[Ee][Ss]2019(\\.([Aa][Rr][Rr][Aa][Yy]|[Oo][Bb][Jj][Ee][Cc][Tt]|[Ss][Tt][Rr][Ii][Nn][Gg]|[Ss][Yy][Mm][Bb][Oo][Ll]))?$"
},
{
"pattern": "^[Ee][Ss]2020(\\.([Bb][Ii][Gg][Ii][Nn][Tt]|[Pp][Rr][Oo][Mm][Ii][Ss][Ee]|[Ss][Tt][Rr][Ii][Nn][Gg]|[Ss][Yy][Mm][Bb][Oo][Ll].[Ww][Ee][Ll][Ll][Kk][Nn][Oo][Ww][Nn]))?$"
},
{
"pattern": "^[Ee][Ss][Nn][Ee][Xx][Tt](\\.([Aa][Rr][Rr][Aa][Yy]|[Aa][Ss][Yy][Nn][Cc][Ii][Tt][Ee][Rr][Aa][Bb][Ll][Ee]|[Bb][Ii][Gg][Ii][Nn][Tt]|[Ii][Nn][Tt][Ll]|[Ss][Yy][Mm][Bb][Oo][Ll]))?$"
},
{
"pattern": "^[Dd][Oo][Mm](\\.[Ii][Tt][Ee][Rr][Aa][Bb][Ll][Ee])?$"
},
{
"pattern": "^[Ss][Cc][Rr][Ii][Pp][Tt][Hh][Oo][Ss][Tt]$"
},
{
"pattern": "^[Ww][Ee][Bb][Ww][Oo][Rr][Kk][Ee][Rr](\\.[Ii][Mm][Pp][Oo][Rr][Tt][Ss][Cc][Rr][Ii][Pp][Tt][Ss])?$"
}
]
}
},
"strictNullChecks": {
"description": "Enable strict null checks. Requires TypeScript version 2.0 or later.",
"type": "boolean"
},
"maxNodeModuleJsDepth": {
"description": "The maximum dependency depth to search under node_modules and load JavaScript files. Only applicable with --allowJs.",
"type": "number",
"default": 0
},
"importHelpers": {
"description": "Import emit helpers (e.g. '__extends', '__rest', etc..) from tslib. Requires TypeScript version 2.1 or later.",
"type": "boolean"
},
"importsNotUsedAsValues": {
"description": "Specify emit/checking behavior for imports that are only used for types",
"type": "string",
"default": "remove",
"enum": [
"remove",
"preserve",
"error"
]
},
"jsxFactory": {
"description": "Specify the JSX factory function to use when targeting react JSX emit, e.g. 'React.createElement' or 'h'. Requires TypeScript version 2.1 or later.",
"type": "string",
"default": "React.createElement"
},
"alwaysStrict": {
"description": "Parse in strict mode and emit 'use strict' for each source file. Requires TypeScript version 2.1 or later.",
"type": "boolean"
},
"strict": {
"description": "Enable all strict type checking options. Requires TypeScript version 2.3 or later.",
"type": "boolean"
},
"strictBindCallApply": {
"description": "Enable stricter checking of of the `bind`, `call`, and `apply` methods on functions.",
"type": "boolean"
},
"downlevelIteration": {
"description": "Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. Requires TypeScript version 2.3 or later.",
"type": "boolean"
},
"checkJs": {
"description": "Report errors in .js files. Requires TypeScript version 2.3 or later.",
"type": "boolean"
},
"strictFunctionTypes": {
"description": "Disable bivariant parameter checking for function types. Requires TypeScript version 2.6 or later.",
"type": "boolean"
},
"strictPropertyInitialization": {
"description": "Ensure non-undefined class properties are initialized in the constructor. Requires TypeScript version 2.7 or later.",
"type": "boolean"
},
"esModuleInterop": {
"description": "Emit '__importStar' and '__importDefault' helpers for runtime babel ecosystem compatibility and enable '--allowSyntheticDefaultImports' for typesystem compatibility. Requires TypeScript version 2.7 or later.",
"type": "boolean"
},
"allowUmdGlobalAccess": {
"description": "Allow accessing UMD globals from modules.",
"type": "boolean"
},
"keyofStringsOnly": {
"description": "Resolve 'keyof' to string valued property names only (no numbers or symbols). Requires TypeScript version 2.9 or later.",
"type": "boolean"
},
"useDefineForClassFields": {
"description": "Emit ECMAScript standard class fields. Requires TypeScript version 3.7 or later.",
"type": "boolean"
},
"declarationMap": {
"description": "Generates a sourcemap for each corresponding '.d.ts' file. Requires TypeScript version 2.9 or later.",
"type": "boolean"
},
"resolveJsonModule": {
"description": "Include modules imported with '.json' extension. Requires TypeScript version 2.9 or later.",
"type": "boolean"
},
"assumeChangesOnlyAffectDirectDependencies": {
"description": "Have recompiles in '--incremental' and '--watch' assume that changes within a file will only affect files directly depending on it.",
"type": "boolean"
}
}
}
}
},
"typeAcquisitionDefinition": {
"properties": {
"typeAcquisition": {
"type": "object",
"description": "Auto type (.d.ts) acquisition options for this project. Requires TypeScript version 2.1 or later.",
"properties": {
"enable": {
"description": "Enable auto type acquisition",
"type": "boolean",
"default": false
},
"include": {
"description": "Specifies a list of type declarations to be included in auto type acquisition. Ex. [\"jquery\", \"lodash\"]",
"type": "array",
"items": {
"type": "string"
}
},
"exclude": {
"description": "Specifies a list of type declarations to be excluded from auto type acquisition. Ex. [\"jquery\", \"lodash\"]",
"type": "array",
"items": {
"type": "string"
}
}
}
}
}
},
"referencesDefinition": {
"properties": {
"references": {
"type": "array",
"description": "Referenced projects. Requires TypeScript version 3.0 or later.",
"items": {
"type": "object",
"description": "Project reference.",
"properties": {
"path": {
"type": "string",
"description": "Path to referenced tsconfig or to folder containing tsconfig."
}
}
}
}
}
},
"tsNodeDefinition": {
"properties": {
"ts-node": {
"description": "ts-node options. See also: https://github.com/TypeStrong/ts-node#configuration-options\n\nts-node offers TypeScript execution and REPL for node.js, with source map support.",
"properties": {
"compiler": {
"default": "typescript",
"description": "Specify a custom TypeScript compiler.",
"type": "string"
},
"compilerHost": {
"default": false,
"description": "Use TypeScript's compiler host API.",
"type": "boolean"
},
"compilerOptions": {
"additionalProperties": true,
"allOf": [
{
"$ref": "#/definitions/compilerOptionsDefinition/properties/compilerOptions"
}
],
"description": "JSON object to merge with compiler options.",
"properties": {},
"type": "object"
},
"emit": {
"default": false,
"description": "Emit output files into `.ts-node` directory.",
"type": "boolean"
},
"files": {
"default": false,
"description": "Load files from `tsconfig.json` on startup.",
"type": "boolean"
},
"ignore": {
"default": "/node_modules/",
"description": "Override the path patterns to skip compilation.",
"items": {
"type": "string"
},
"type": "array"
},
"ignoreDiagnostics": {
"description": "Ignore TypeScript warnings by diagnostic code.",
"items": {
"type": [
"string",
"number"
]
},
"type": "array"
},
"logError": {
"default": false,
"description": "Logs TypeScript errors to stderr instead of throwing exceptions.",
"type": "boolean"
},
"preferTsExts": {
"default": false,
"description": "Re-order file extensions so that TypeScript imports are preferred.",
"type": "boolean"
},
"pretty": {
"default": false,
"description": "Use pretty diagnostic formatter.",
"type": "boolean"
},
"scope": {
"default": false,
"description": "Scope compiler to files within `cwd`.",
"type": "boolean"
},
"skipIgnore": {
"default": false,
"description": "Skip ignore check.",
"type": "boolean"
},
"transpileOnly": {
"default": false,
"description": "Use TypeScript's faster `transpileModule`.",
"type": "boolean"
},
"typeCheck": {
"default": true,
"description": "**DEPRECATED** Specify type-check is enabled (e.g. `transpileOnly == false`).",
"type": "boolean"
}
},
"type": "object"
}
}
}
},
"type": "object",
"allOf": [
{
"$ref": "#/definitions/compilerOptionsDefinition"
},
{
"$ref": "#/definitions/compileOnSaveDefinition"
},
{
"$ref": "#/definitions/typeAcquisitionDefinition"
},
{
"$ref": "#/definitions/extendsDefinition"
},
{
"$ref": "#/definitions/tsNodeDefinition"
},
{
"$ref": "#/definitions/tsNodeDefinition"
},
{
"anyOf": [
{
"$ref": "#/definitions/filesDefinition"
},
{
"$ref": "#/definitions/excludeDefinition"
},
{
"$ref": "#/definitions/includeDefinition"
},
{
"$ref": "#/definitions/referencesDefinition"
}
]
}
]
}