Skip to content

Proposal: Modularize Library #6974

Closed
Closed
@yuit

Description

@yuit

Problem

Currently TypeScript compiler accepts a single compiler option, target, which specify both version of library to be included during compilation and version of JavaScript for emitting code together.
The behaviour presents limitations in two parts of the pipeline: consuming the default library and granularly controlling how JavaScript will be emitted (e.g. what features to be down-level etc.).
The proposal will mainly focus on the first issue regarding using the default library.

The current behavior of target option doesn't allow users to have a fine-grain control on what library or feature of the library to be included, and user cannot independently control library's version from emit JavaScript version. As summarized in #4692 Proposal: Granular Targeting and #4168 Normalize our lib files by compiler setting

  • Emit ES5 JavaScript while using ES6 library during design-time (and vice-versa).
  • Include only sub-part of the ES6/ESnext library
  • Modifying default libraries can conflict with users-defined ones.
  • Using host-specific library.

Workaround

As @yortus points out in the #4692 Proposal: Granular Targeting , there are possible workarounds for above issues by maintaing customized version of the default library while target another version of emit JavaScript.
Such approach is cumbersome to maintain and consume any necessary fixes of the default library.

Related Issues:

  • #4692 Proposal: Granular Targeting
  • #4168 Normalize our lib files by compiler settings
  • #3215 New APIs added to lib.d.ts may break client codes. Allow duplicated members in interfaces? Make lib.d.ts overridable?
  • #3005 Using ES6 type default library when targetting ES5 output

Proposed Solution

There are two parts to the proposed solution:

  1. Introducing a new compiler flag --lib. The flag will be used to allow users to granularly control the default library.
    Note: target flag will remain. Its behaviors with --lib flag will be discussed below.
  2. Breaking down the default library into smaller files, especially ES6 library and any future JavaScript library.

Compiler Flag --lib

The flag's options (see below for the full list) allows users to specify what library to be included into the compilation.
The flag's options can be separated into following categories:

  • JavaScript only:

    es3

    es5

    es6

  • Host only:

    node

    dom

    dom.iterable

    webworker

    scripthost

  • ES6 or ESNext by-features options:

    es6.array

    es6.collection

    es6.function

    es6.generator

    es6.iterable

    es6.math

    es6.number

    es6.object

    es6.promise

    es6.proxy

    es6.reflect

    es6.regexp

    es6.string

    es6.symbol

    es6.symbol.wellknown

    es7.array.include

The --lib flag is an optional flag and multiple options can be used in combination (e.g --lib es6,dom.iterable) and each option will be mapped to associated library.
So in this example, files: lib.es6.d.ts and lib.dom.iterable.d.ts will be loaded into the compilation..
When --lib is specified, --target will be used solely to indicate version of emitting JavaScript.

In additional to above behavior, we still need to determine what to be included when --lib is not specified, should it remain the same, including version of library specifying by --target and all host libraries, or including every library. -> _Current implementation is to include version of the library using --target

The proposal will only affect when the compiler attempts to create compilation in Program.ts. Other parts of the pipeline will not be affected by the proposal.

Usage:

The --lib flag will take an options in the form of string separated by comma. Space will not be allowed as a separator. This rule apply to both command line and tsconfig

Valid

tsc --target es5 --lib es6
tsc --target es5 --lib es5,es6.array
"compilerOptions": {
    ...
    "lib": "es5,es6.array"
}

Invalid command-line

tsc --target es5--lib es5, es6.array  // es6.array will be considered a file-name
tsc --target es5 --lib es5 es6.array  // es6.array will be considered a file-name
"compilerOptions": {
    ...
    "lib": "es5, es6.array"
}

Working Items:

Metadata

Metadata

Assignees

Labels

@typesRelates to working with .d.ts files (declaration/definition files) from DefinitelyTypedCommittedThe team has roadmapped this issueFixedA PR has been merged for this issueSuggestionAn idea for TypeScript

Type

No type

Projects

No projects

Relationships

None yet

Development

No branches or pull requests

Issue actions