{"componentChunkName":"component---src-templates-handbook-tsx","path":"/docs/handbook/release-notes/typescript-3-5.html","result":{"data":{"allSitePage":{"nodes":[{"path":"/dev-404-page/"},{"path":"/docs/handbook/advanced-types.html"},{"path":"/docs/handbook/basic-types.html"},{"path":"/docs/handbook/classes.html"},{"path":"/docs/handbook/compiler-options-in-msbuild.html"},{"path":"/docs/handbook/compiler-options.html"},{"path":"/docs/handbook/configuring-watch.html"},{"path":"/docs/handbook/declaration-merging.html"},{"path":"/docs/handbook/decorators.html"},{"path":"/docs/handbook/enums.html"},{"path":"/docs/handbook/functions.html"},{"path":"/docs/handbook/generics.html"},{"path":"/docs/handbook/integrating-with-build-tools.html"},{"path":"/docs/handbook/interfaces.html"},{"path":"/docs/handbook/iterators-and-generators.html"},{"path":"/docs/handbook/jsdoc-supported-types.html"},{"path":"/docs/handbook/jsx.html"},{"path":"/docs/handbook/literal-types.html"},{"path":"/docs/handbook/mixins.html"},{"path":"/docs/handbook/module-resolution.html"},{"path":"/docs/handbook/modules.html"},{"path":"/docs/handbook/namespaces-and-modules.html"},{"path":"/docs/handbook/namespaces.html"},{"path":"/docs/handbook/nightly-builds.html"},{"path":"/docs/handbook/project-references.html"},{"path":"/docs/handbook/symbols.html"},{"path":"/docs/handbook/"},{"path":"/docs/handbook/triple-slash-directives.html"},{"path":"/docs/handbook/type-checking-javascript-files.html"},{"path":"/docs/handbook/type-compatibility.html"},{"path":"/docs/handbook/type-inference.html"},{"path":"/docs/handbook/unions-and-intersections.html"},{"path":"/docs/handbook/utility-types.html"},{"path":"/docs/handbook/variable-declarations.html"},{"path":"/docs/handbook/writing-declaration-files.html"},{"path":"/docs/handbook/declaration-files/by-example.html"},{"path":"/docs/handbook/declaration-files/consumption.html"},{"path":"/docs/handbook/declaration-files/deep-dive.html"},{"path":"/docs/handbook/declaration-files/do-s-and-don-ts.html"},{"path":"/docs/handbook/declaration-files/introduction.html"},{"path":"/docs/handbook/declaration-files/library-structures.html"},{"path":"/docs/handbook/declaration-files/publishing.html"},{"path":"/docs/handbook/declaration-files/templates.html"},{"path":"/docs/handbook/release-notes/typescript-1-1.html"},{"path":"/docs/handbook/release-notes/typescript-1-3.html"},{"path":"/docs/handbook/release-notes/typescript-1-4.html"},{"path":"/docs/handbook/release-notes/typescript-1-5.html"},{"path":"/docs/handbook/release-notes/typescript-1-6.html"},{"path":"/docs/handbook/release-notes/typescript-1-7.html"},{"path":"/docs/handbook/release-notes/typescript-1-8.html"},{"path":"/docs/handbook/release-notes/typescript-2-0.html"},{"path":"/docs/handbook/release-notes/typescript-2-2.html"},{"path":"/docs/handbook/release-notes/typescript-2-1.html"},{"path":"/docs/handbook/release-notes/typescript-2-3.html"},{"path":"/docs/handbook/release-notes/typescript-2-4.html"},{"path":"/docs/handbook/release-notes/typescript-2-5.html"},{"path":"/docs/handbook/release-notes/typescript-2-6.html"},{"path":"/docs/handbook/release-notes/typescript-2-7.html"},{"path":"/docs/handbook/release-notes/typescript-2-8.html"},{"path":"/docs/handbook/release-notes/typescript-2-9.html"},{"path":"/docs/handbook/release-notes/typescript-3-0.html"},{"path":"/docs/handbook/release-notes/typescript-3-1.html"},{"path":"/docs/handbook/release-notes/typescript-3-2.html"},{"path":"/docs/handbook/release-notes/typescript-3-3.html"},{"path":"/docs/handbook/release-notes/typescript-3-4.html"},{"path":"/docs/handbook/release-notes/typescript-3-5.html"},{"path":"/docs/handbook/release-notes/typescript-3-6.html"},{"path":"/docs/handbook/release-notes/typescript-3-7.html"},{"path":"/docs/handbook/release-notes/typescript-3-8.html"},{"path":"/docs/handbook/asp-net-core.html"},{"path":"/docs/handbook/angular.html"},{"path":"/docs/handbook/dom-manipulation.html"},{"path":"/docs/handbook/gulp.html"},{"path":"/docs/handbook/migrating-from-javascript.html"},{"path":"/docs/handbook/react-&-webpack.html"},{"path":"/docs/handbook/react.html"},{"path":"/docs/handbook/typescript-in-5-minutes-func.html"},{"path":"/docs/handbook/typescript-in-5-minutes.html"},{"path":"/docs/handbook/typescript-in-5-minutes-oop.html"},{"path":"/docs/handbook/typescript-from-scratch.html"},{"path":"/docs/handbook/typescript-tooling-in-5-minutes.html"},{"path":"/docs/handbook/tsconfig-json.html"},{"path":"/docs/handbook/declaration-files/templates/global-modifying-module-d-ts.html"},{"path":"/docs/handbook/declaration-files/templates/global-plugin-d-ts.html"},{"path":"/docs/handbook/declaration-files/templates/global-d-ts.html"},{"path":"/docs/handbook/declaration-files/templates/module-class-d-ts.html"},{"path":"/docs/handbook/declaration-files/templates/module-function-d-ts.html"},{"path":"/docs/handbook/declaration-files/templates/module-plugin-d-ts.html"},{"path":"/docs/handbook/declaration-files/templates/module-d-ts.html"},{"path":"/docs/handbook/release-notes/overview.html"},{"path":"/tsconfig"},{"path":"/en/tsconfig"},{"path":"/ja/tsconfig"},{"path":"/vo/tsconfig"},{"path":"/play"},{"path":"/en/play"},{"path":"/es/play"},{"path":"/vo/play"},{"path":"/zh/play"},{"path":"/ja/play"},{"path":"/play/3-7/fixits/big-number-literals.ts"},{"path":"/play/3-7/fixits/const-to-let.ts"},{"path":"/play/3-7/fixits/infer-from-usage-changes.ts"},{"path":"/play/3-7/syntax-and-messaging/flattened-error-reporting.ts"},{"path":"/play/3-7/syntax-and-messaging/nullish-coalescing.ts"},{"path":"/play/3-7/syntax-and-messaging/optional-chaining.ts"},{"path":"/play/3-7/types-and-code-flow/assertion-functions.ts"},{"path":"/play/3-7/types-and-code-flow/recursive-type-references.ts"},{"path":"/play/3-7/types-and-code-flow/uncalled-function-checks.ts"},{"path":"/play/3-8/breaking-changes/checking-unions-with-index-signatures.ts"},{"path":"/play/3-8/jsdoc-improvements/accessibility-modifiers.js"},{"path":"/play/3-8/syntax-and-messaging/export-modules-from.ts"},{"path":"/play/3-8/syntax-and-messaging/private-class-fields.ts"},{"path":"/play/javascript/external-apis/typescript-with-deno.ts"},{"path":"/play/javascript/external-apis/typescript-with-node.js"},{"path":"/play/javascript/external-apis/typescript-with-web.js"},{"path":"/play/javascript/external-apis/typescript-with-webgl.js"},{"path":"/play/javascript/functions-with-javascript/function-chaining.ts"},{"path":"/play/javascript/functions-with-javascript/generic-functions.ts"},{"path":"/play/javascript/functions-with-javascript/typing-functions.ts"},{"path":"/play/javascript/helping-with-javascript/errors.ts"},{"path":"/play/javascript/helping-with-javascript/quick-fixes.ts"},{"path":"/play/javascript/javascript-essentials/code-flow.ts"},{"path":"/play/javascript/javascript-essentials/functions.ts"},{"path":"/play/javascript/javascript-essentials/hello-world.ts"},{"path":"/play/javascript/javascript-essentials/objects-and-arrays.ts"},{"path":"/play/javascript/modern-javascript/async-await.ts"},{"path":"/play/javascript/modern-javascript/immutability.ts"},{"path":"/play/javascript/modern-javascript/import-export.ts"},{"path":"/play/javascript/modern-javascript/jsdoc-support.js"},{"path":"/play/javascript/working-with-classes/classes-101.ts"},{"path":"/play/javascript/working-with-classes/generic-classes.ts"},{"path":"/play/javascript/working-with-classes/mixins.ts"},{"path":"/play/javascript/working-with-classes/this.ts"},{"path":"/play/playground/config/javascript-playgrounds.js"},{"path":"/play/playground/config/new-compiler-defaults.ts"},{"path":"/play/playground/language/automatic-type-acquisition.ts"},{"path":"/play/playground/language/fixits.ts"},{"path":"/play/playground/tooling/mobile-support.ts"},{"path":"/play/playground/tooling/sharable-urls.ts"},{"path":"/play/playground/tooling/typescript-versions.ts"},{"path":"/play/typescript/language/soundness.ts"},{"path":"/play/typescript/language/structural-typing.ts"},{"path":"/play/typescript/language/type-guards.ts"},{"path":"/play/typescript/language/type-widening-and-narrowing.ts"},{"path":"/play/typescript/language-extensions/enums.ts"},{"path":"/play/typescript/language-extensions/nominal-typing.ts"},{"path":"/play/typescript/language-extensions/types-vs-interfaces.ts"},{"path":"/play/typescript/meta-types/conditional-types.ts"},{"path":"/play/typescript/meta-types/discriminate-types.ts"},{"path":"/play/typescript/meta-types/indexed-types.ts"},{"path":"/play/typescript/meta-types/mapped-types.ts"},{"path":"/play/typescript/primitives/any.ts"},{"path":"/play/typescript/primitives/literals.ts"},{"path":"/play/typescript/primitives/union-and-intersection-types.ts"},{"path":"/play/typescript/primitives/unknown-and-never.ts"},{"path":"/play/typescript/type-primitives/built-in-utility-types.ts"},{"path":"/play/typescript/type-primitives/nullable-types.ts"},{"path":"/play/typescript/type-primitives/tuples.ts"},{"path":"/es/play/javascript/external-apis/typescript-with-deno.ts"},{"path":"/es/play/javascript/external-apis/typescript-with-node.js"},{"path":"/es/play/javascript/external-apis/typescript-with-web.js"},{"path":"/es/play/javascript/functions-with-javascript/function-chaining.ts"},{"path":"/es/play/javascript/functions-with-javascript/generic-functions.ts"},{"path":"/es/play/javascript/javascript-essentials/hello-world.ts"},{"path":"/es/play/javascript/javascript-essentials/objects-and-arrays.ts"},{"path":"/es/play/typescript/type-primitives/built-in-utility-types.ts"},{"path":"/es/play/typescript/type-primitives/nullable-types.ts"},{"path":"/es/play/typescript/type-primitives/tuples.ts"},{"path":"/ja/play/typescript/language-extensions/enums.ts"},{"path":"/ja/play/typescript/language-extensions/nominal-typing.ts"},{"path":"/ja/play/typescript/language-extensions/types-vs-interfaces.ts"},{"path":"/ja/play/typescript/primitives/any.ts"},{"path":"/ja/play/typescript/primitives/literals.ts"},{"path":"/ja/play/typescript/primitives/union-and-intersection-types.ts"},{"path":"/ja/play/typescript/type-primitives/built-in-utility-types.ts"},{"path":"/vo/play/javascript/javascript-essentials/code-flow.ts"},{"path":"/vo/play/javascript/javascript-essentials/functions.ts"},{"path":"/vo/play/javascript/javascript-essentials/hello-world.ts"},{"path":"/vo/play/javascript/javascript-essentials/objects-and-arrays.ts"},{"path":"/zh/play/javascript/external-apis/typescript-with-deno.ts"},{"path":"/zh/play/javascript/external-apis/typescript-with-node.js"},{"path":"/zh/play/javascript/external-apis/typescript-with-web.js"},{"path":"/zh/play/javascript/external-apis/typescript-with-webgl.js"},{"path":"/zh/play/javascript/functions-with-javascript/function-chaining.ts"},{"path":"/zh/play/javascript/functions-with-javascript/generic-functions.ts"},{"path":"/zh/play/javascript/functions-with-javascript/typing-functions.ts"},{"path":"/zh/play/javascript/helping-with-javascript/errors.ts"},{"path":"/zh/play/javascript/helping-with-javascript/quick-fixes.ts"},{"path":"/zh/play/javascript/javascript-essentials/code-flow.ts"},{"path":"/zh/play/javascript/javascript-essentials/functions.ts"},{"path":"/zh/play/javascript/javascript-essentials/hello-world.ts"},{"path":"/zh/play/javascript/modern-javascript/import-export.ts"},{"path":"/zh/play/javascript/modern-javascript/jsdoc-support.js"},{"path":"/zh/play/javascript/working-with-classes/classes-101.ts"},{"path":"/zh/play/javascript/working-with-classes/generic-classes.ts"},{"path":"/zh/play/javascript/working-with-classes/mixins.ts"},{"path":"/zh/play/javascript/working-with-classes/this.ts"},{"path":"/zh/play/playground/config/javascript-playgrounds.js"},{"path":"/zh/play/playground/config/new-compiler-defaults.ts"},{"path":"/zh/play/playground/language/automatic-type-acquisition.ts"},{"path":"/zh/play/playground/language/fixits.ts"},{"path":"/zh/play/playground/tooling/mobile-support.ts"},{"path":"/zh/play/playground/tooling/sharable-urls.ts"},{"path":"/zh/play/playground/tooling/typescript-versions.ts"},{"path":"/zh/play/typescript/language/soundness.ts"},{"path":"/zh/play/typescript/language/structural-typing.ts"},{"path":"/zh/play/typescript/language/type-guards.ts"},{"path":"/zh/play/typescript/language/type-widening-and-narrowing.ts"},{"path":"/zh/play/typescript/language-extensions/enums.ts"},{"path":"/zh/play/typescript/language-extensions/nominal-typing.ts"},{"path":"/zh/play/typescript/language-extensions/types-vs-interfaces.ts"},{"path":"/zh/play/typescript/meta-types/conditional-types.ts"},{"path":"/zh/play/typescript/meta-types/discriminate-types.ts"},{"path":"/zh/play/typescript/meta-types/indexed-types.ts"},{"path":"/zh/play/typescript/meta-types/mapped-types.ts"},{"path":"/zh/play/typescript/primitives/any.ts"},{"path":"/zh/play/typescript/primitives/literals.ts"},{"path":"/zh/play/typescript/primitives/union-and-intersection-types.ts"},{"path":"/zh/play/typescript/primitives/unknown-and-never.ts"},{"path":"/zh/play/typescript/type-primitives/built-in-utility-types.ts"},{"path":"/zh/play/typescript/type-primitives/nullable-types.ts"},{"path":"/zh/play/typescript/type-primitives/tuples.ts"},{"path":"/zh/play/javascript/modern-javascript/immutability.ts"},{"path":"/zh/play/javascript/modern-javascript/async-await.ts"},{"path":"/zh/play/javascript/javascript-essentials/objects-and-arrays.ts"},{"path":"/community"},{"path":"/es/community"},{"path":"/ja/community"},{"path":"/vo/community"},{"path":"/zh/community"},{"path":"/download"},{"path":"/es/download"},{"path":"/ja/download"},{"path":"/vo/download"},{"path":"/zh/download"},{"path":"/empty"},{"path":"/es/empty"},{"path":"/ja/empty"},{"path":"/vo/empty"},{"path":"/zh/empty"},{"path":"/"},{"path":"/es/"},{"path":"/ja/"},{"path":"/vo/"},{"path":"/zh/"},{"path":"/tools"},{"path":"/es/tools"},{"path":"/ja/tools"},{"path":"/vo/tools"},{"path":"/zh/tools"},{"path":"/why-create-typescript"},{"path":"/es/why-create-typescript"},{"path":"/ja/why-create-typescript"},{"path":"/vo/why-create-typescript"},{"path":"/zh/why-create-typescript"},{"path":"/docs/home"},{"path":"/es/docs/home"},{"path":"/ja/docs/home"},{"path":"/vo/docs/home"},{"path":"/zh/docs/home"},{"path":"/dev/playground-plugins/"},{"path":"/dev/sandbox/"},{"path":"/dev/twoslash/"},{"path":"/dev/typescript-vfs/"}]},"markdownRemark":{"id":"694b4b27-def9-5e14-8b87-51519de47dac","excerpt":"Speed improvements TypeScript 3.5 introduces several optimizations around type-checking and incremental builds. Type-checking speed-ups TypeScript 3.5 contains…","html":"<h2 id=\"speed-improvements\" style=\"position:relative;\"><a href=\"#speed-improvements\" aria-label=\"speed improvements permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Speed improvements</h2>\n<p>TypeScript 3.5 introduces several optimizations around type-checking and incremental builds.</p>\n<h3 id=\"type-checking-speed-ups\" style=\"position:relative;\"><a href=\"#type-checking-speed-ups\" aria-label=\"type checking speed ups permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Type-checking speed-ups</h3>\n<p>TypeScript 3.5 contains certain optimizations over TypeScript 3.4 for type-checking more efficiently.\nThese improvements are significantly more pronounced in editor scenarios where type-checking drives operations like code completion lists.</p>\n<h3 id=\"--incremental-improvements\" style=\"position:relative;\"><a href=\"#--incremental-improvements\" aria-label=\"  incremental improvements permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a><code>--incremental</code> improvements</h3>\n<p>TypeScript 3.5 improves on 3.4’s <code>--incremental</code> build mode, by saving information about how the state of the world was calculated - compiler settings, why files were looked up, where files were found, etc.\nIn scenarios involving hundreds of projects using TypeScript’s project references in <code>--build</code> mode, <a href=\"https://github.com/Microsoft/TypeScript/pull/31101\">we’ve found that the amount of time rebuilding can be reduced by as much as 68% compared to TypeScript 3.4</a>!</p>\n<p>For more details, you can see the pull requests to</p>\n<ul>\n<li><a href=\"https://github.com/Microsoft/TypeScript/pull/31100\">cache module resolution</a></li>\n<li><a href=\"https://github.com/Microsoft/TypeScript/pull/31101\">cache settings calculated from <code>tsconfig.json</code></a></li>\n</ul>\n<h2 id=\"the-omit-helper-type\" style=\"position:relative;\"><a href=\"#the-omit-helper-type\" aria-label=\"the omit helper type permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>The <code>Omit</code> helper type</h2>\n<p>TypeScript 3.5 introduces the new <code>Omit</code> helper type, which creates a new type with some properties dropped from the original.</p>\n<pre class=\"shiki\"><div class=\"language-id\">ts</div><div class='code-container'><code><span style=\"color: #0000FF\">type</span><span style=\"color: #000000\"> Person = {</span>\n<span style=\"color: #000000\">    name: string;</span>\n<span style=\"color: #000000\">    age: number;</span>\n<span style=\"color: #000000\">    location: string;</span>\n<span style=\"color: #000000\">};</span>\n\n<span style=\"color: #0000FF\">type</span><span style=\"color: #000000\"> QuantumPerson = Omit&lt;Person, </span><span style=\"color: #A31515\">\"location\"</span><span style=\"color: #000000\">&gt;;</span>\n\n<span style=\"color: #008000\">// equivalent to</span>\n<span style=\"color: #0000FF\">type</span><span style=\"color: #000000\"> QuantumPerson = {</span>\n<span style=\"color: #000000\">    name: string;</span>\n<span style=\"color: #000000\">    age: number;</span>\n<span style=\"color: #000000\">};</span></code></div></pre>\n<p>Here we were able to copy over all the properties of <code>Person</code> except for <code>location</code> using the <code>Omit</code> helper.</p>\n<p>For more details, <a href=\"https://github.com/Microsoft/TypeScript/pull/30552\">see the pull request on GitHub to add <code>Omit</code></a>, as well as <a href=\"https://github.com/microsoft/TypeScript/pull/31134\">the change to use <code>Omit</code> for object rest</a>.</p>\n<h3 id=\"improved-excess-property-checks-in-union-types\" style=\"position:relative;\"><a href=\"#improved-excess-property-checks-in-union-types\" aria-label=\"improved excess property checks in union types permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Improved excess property checks in union types</h3>\n<p>In TypeScript 3.4 and earlier, certain excess properties were allowed in situations where they really shouldn’t have been.\nFor instance, TypeScript 3.4 permitted the incorrect <code>name</code> property in the object literal even though its types don’t match between <code>Point</code> and <code>Label</code>.</p>\n<pre class=\"shiki\"><div class=\"language-id\">ts</div><div class='code-container'><code><span style=\"color: #0000FF\">type</span><span style=\"color: #000000\"> Point = {</span>\n<span style=\"color: #000000\">    x: number;</span>\n<span style=\"color: #000000\">    y: number;</span>\n<span style=\"color: #000000\">};</span>\n\n<span style=\"color: #0000FF\">type</span><span style=\"color: #000000\"> Label = {</span>\n<span style=\"color: #000000\">    name: string;</span>\n<span style=\"color: #000000\">};</span>\n\n<span style=\"color: #0000FF\">const</span><span style=\"color: #000000\"> thing: Point | Label = {</span>\n<span style=\"color: #000000\">    x: </span><span style=\"color: #09835A\">0</span><span style=\"color: #000000\">,</span>\n<span style=\"color: #000000\">    y: </span><span style=\"color: #09835A\">0</span><span style=\"color: #000000\">,</span>\n<span style=\"color: #000000\">    name: </span><span style=\"color: #0000FF\">true</span><span style=\"color: #000000\"> </span><span style=\"color: #008000\">// uh-oh!</span>\n<span style=\"color: #000000\">};</span></code></div></pre>\n<p>Previously, a non-disciminated union wouldn’t have <em>any</em> excess property checking done on its members, and as a result, the incorrectly typed <code>name</code> property slipped by.</p>\n<p>In TypeScript 3.5, the type-checker at least verifies that all the provided properties belong to <em>some</em> union member and have the appropriate type, meaning that the sample above correctly issues an error.</p>\n<p>Note that partial overlap is still permitted as long as the property types are valid.</p>\n<pre class=\"shiki\"><div class=\"language-id\">ts</div><div class='code-container'><code><span style=\"color: #0000FF\">const</span><span style=\"color: #000000\"> pl: Point | Label = {</span>\n<span style=\"color: #000000\">    x: </span><span style=\"color: #09835A\">0</span><span style=\"color: #000000\">,</span>\n<span style=\"color: #000000\">    y: </span><span style=\"color: #09835A\">0</span><span style=\"color: #000000\">,</span>\n<span style=\"color: #000000\">    name: </span><span style=\"color: #A31515\">\"origin\"</span><span style=\"color: #000000\"> </span><span style=\"color: #008000\">// okay</span>\n<span style=\"color: #000000\">};</span></code></div></pre>\n<h2 id=\"the---allowumdglobalaccess-flag\" style=\"position:relative;\"><a href=\"#the---allowumdglobalaccess-flag\" aria-label=\"the   allowumdglobalaccess flag permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>The <code>--allowUmdGlobalAccess</code> flag</h2>\n<p>In TypeScript 3.5, you can now reference UMD global declarations like</p>\n<pre><code>export as namespace foo;\n</code></pre>\n<p>from anywhere - even modules - using the new <code>--allowUmdGlobalAccess</code> flag.</p>\n<p>This mode adds flexibility for mixing and matching the way 3rd party libraries, where globals that libraries declare can always be consumed, even from within modules.</p>\n<p>For more details, <a href=\"https://github.com/Microsoft/TypeScript/pull/30776/files\">see the pull request on GitHub</a>.</p>\n<h2 id=\"smarter-union-type-checking\" style=\"position:relative;\"><a href=\"#smarter-union-type-checking\" aria-label=\"smarter union type checking permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Smarter union type checking</h2>\n<p>In TypeScript 3.4 and prior, the following example would fail:</p>\n<pre class=\"shiki\"><div class=\"language-id\">ts</div><div class='code-container'><code><span style=\"color: #0000FF\">type</span><span style=\"color: #000000\"> S = { done: boolean, value: number }</span>\n<span style=\"color: #0000FF\">type</span><span style=\"color: #000000\"> T =</span>\n<span style=\"color: #000000\">    | { done: false, value: number }</span>\n<span style=\"color: #000000\">    | { done: true, value: number };</span>\n\n<span style=\"color: #0000FF\">declare</span><span style=\"color: #000000\"> </span><span style=\"color: #0000FF\">let</span><span style=\"color: #000000\"> source: S;</span>\n<span style=\"color: #0000FF\">declare</span><span style=\"color: #000000\"> </span><span style=\"color: #0000FF\">let</span><span style=\"color: #000000\"> target: T;</span>\n\n<span style=\"color: #000000\">target = source;</span></code></div></pre>\n<p>That’s because <code>S</code> isn’t assignable to <code>{ done: false, value: number }</code> nor <code>{ done: true, value: number }</code>.\nWhy?\nBecause the <code>done</code> property in <code>S</code> isn’t specific enough - it’s <code>boolean</code> whereas each constituent of <code>T</code> has a <code>done</code> property that’s specifically <code>true</code> or <code>false</code>.\nThat’s what we meant by each constituent type being checked in isolation: TypeScript doesn’t just union each property together and see if <code>S</code> is assignable to that.\nIf it did, some bad code could get through like the following:</p>\n<pre class=\"shiki\"><div class=\"language-id\">ts</div><div class='code-container'><code><span style=\"color: #0000FF\">interface</span><span style=\"color: #000000\"> Foo {</span>\n<span style=\"color: #000000\">    kind: </span><span style=\"color: #A31515\">\"foo\"</span><span style=\"color: #000000\">;</span>\n<span style=\"color: #000000\">    value: string;</span>\n<span style=\"color: #000000\">}</span>\n\n<span style=\"color: #0000FF\">interface</span><span style=\"color: #000000\"> Bar {</span>\n<span style=\"color: #000000\">    kind: </span><span style=\"color: #A31515\">\"bar\"</span><span style=\"color: #000000\">;</span>\n<span style=\"color: #000000\">    value: number;</span>\n<span style=\"color: #000000\">}</span>\n\n<span style=\"color: #0000FF\">function</span><span style=\"color: #000000\"> doSomething(x: Foo | Bar) {</span>\n<span style=\"color: #000000\">    </span><span style=\"color: #0000FF\">if</span><span style=\"color: #000000\"> (x.kind === </span><span style=\"color: #A31515\">\"foo\"</span><span style=\"color: #000000\">) {</span>\n<span style=\"color: #000000\">        x.value.toLowerCase();</span>\n<span style=\"color: #000000\">    }</span>\n<span style=\"color: #000000\">}</span>\n\n<span style=\"color: #008000\">// uh-oh - luckily TypeScript errors here!</span>\n<span style=\"color: #000000\">doSomething({</span>\n<span style=\"color: #000000\">    kind: </span><span style=\"color: #A31515\">\"foo\"</span><span style=\"color: #000000\">,</span>\n<span style=\"color: #000000\">    value: </span><span style=\"color: #09835A\">123</span><span style=\"color: #000000\">,</span>\n<span style=\"color: #000000\">});</span></code></div></pre>\n<p>However, this was a bit overly strict for the original example.\nIf you figure out the precise type of any possible value of <code>S</code>, you can actually see that it matches the types in <code>T</code> exactly.</p>\n<p>In TypeScript 3.5, when assigning to types with discriminant properties like in <code>T</code>, the language actually <em>will</em> go further and decompose types like <code>S</code> into a union of every possible inhabitant type.\nIn this case, since <code>boolean</code> is a union of <code>true</code> and <code>false</code>, <code>S</code> will be viewed as a union of <code>{ done: false, value: number }</code> and <code>{ done: true, value: number }</code>.</p>\n<p>For more details, you can <a href=\"https://github.com/microsoft/TypeScript/pull/30779\">see the original pull request on GitHub</a>.</p>\n<h2 id=\"higher-order-type-inference-from-generic-constructors\" style=\"position:relative;\"><a href=\"#higher-order-type-inference-from-generic-constructors\" aria-label=\"higher order type inference from generic constructors permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Higher order type inference from generic constructors</h2>\n<p>In TypeScript 3.4, we improved inference for when generic functions that return functions like so:</p>\n<pre class=\"shiki\"><div class=\"language-id\">ts</div><div class='code-container'><code><span style=\"color: #0000FF\">function</span><span style=\"color: #000000\"> compose&lt;T, U, V&gt;(</span>\n<span style=\"color: #000000\">    f: (x: T) </span><span style=\"color: #0000FF\">=&gt;</span><span style=\"color: #000000\"> U, g: (y: U) </span><span style=\"color: #0000FF\">=&gt;</span><span style=\"color: #000000\"> V): (x: T) </span><span style=\"color: #0000FF\">=&gt;</span><span style=\"color: #000000\"> V {</span>\n<span style=\"color: #000000\">    </span>\n<span style=\"color: #000000\">    </span><span style=\"color: #0000FF\">return</span><span style=\"color: #000000\"> x </span><span style=\"color: #0000FF\">=&gt;</span><span style=\"color: #000000\"> g(f(x))</span>\n<span style=\"color: #000000\">}</span></code></div></pre>\n<p>took other generic functions as arguments, like so:</p>\n<pre class=\"shiki\"><div class=\"language-id\">ts</div><div class='code-container'><code><span style=\"color: #0000FF\">function</span><span style=\"color: #000000\"> arrayify&lt;T&gt;(x: T): T[] {</span>\n<span style=\"color: #000000\">    </span><span style=\"color: #0000FF\">return</span><span style=\"color: #000000\"> [x];</span>\n<span style=\"color: #000000\">}</span>\n\n<span style=\"color: #0000FF\">type</span><span style=\"color: #000000\"> Box&lt;U&gt; = { value: U }</span>\n<span style=\"color: #0000FF\">function</span><span style=\"color: #000000\"> boxify&lt;U&gt;(y: U): Box&lt;U&gt; {</span>\n<span style=\"color: #000000\">    </span><span style=\"color: #0000FF\">return</span><span style=\"color: #000000\"> { value: y };</span>\n<span style=\"color: #000000\">}</span>\n\n<span style=\"color: #0000FF\">let</span><span style=\"color: #000000\"> newFn = compose(arrayify, boxify);</span></code></div></pre>\n<p>Instead of a relatively useless type like <code>(x: {}) => Box&#x3C;{}[]></code>, which older versions of the language would infer, TypeScript 3.4’s inference allows <code>newFn</code> to be generic.\nIts new type is <code>&#x3C;T>(x: T) => Box&#x3C;T[]></code>.</p>\n<p>TypeScript 3.5 generalizes this behavior to work on constructor functions as well.</p>\n<pre class=\"shiki\"><div class=\"language-id\">ts</div><div class='code-container'><code><span style=\"color: #0000FF\">class</span><span style=\"color: #000000\"> Box&lt;T&gt; {</span>\n<span style=\"color: #000000\">    kind: </span><span style=\"color: #A31515\">\"box\"</span><span style=\"color: #000000\">;</span>\n<span style=\"color: #000000\">    value: T;</span>\n<span style=\"color: #000000\">    </span><span style=\"color: #0000FF\">constructor</span><span style=\"color: #000000\">(value: T) {</span>\n<span style=\"color: #000000\">        </span><span style=\"color: #0000FF\">this</span><span style=\"color: #000000\">.value = value;</span>\n<span style=\"color: #000000\">    }</span>\n<span style=\"color: #000000\">}</span>\n\n<span style=\"color: #0000FF\">class</span><span style=\"color: #000000\"> Bag&lt;U&gt; {</span>\n<span style=\"color: #000000\">    kind: </span><span style=\"color: #A31515\">\"bag\"</span><span style=\"color: #000000\">;</span>\n<span style=\"color: #000000\">    value: U;</span>\n<span style=\"color: #000000\">    </span><span style=\"color: #0000FF\">constructor</span><span style=\"color: #000000\">(value: U) {</span>\n<span style=\"color: #000000\">        </span><span style=\"color: #0000FF\">this</span><span style=\"color: #000000\">.value = value;</span>\n<span style=\"color: #000000\">    }</span>\n<span style=\"color: #000000\">}</span>\n\n\n<span style=\"color: #0000FF\">function</span><span style=\"color: #000000\"> composeCtor&lt;T, U, V&gt;(</span>\n<span style=\"color: #000000\">    F: </span><span style=\"color: #0000FF\">new</span><span style=\"color: #000000\"> (x: T) </span><span style=\"color: #0000FF\">=&gt;</span><span style=\"color: #000000\"> U, G: </span><span style=\"color: #0000FF\">new</span><span style=\"color: #000000\"> (y: U) </span><span style=\"color: #0000FF\">=&gt;</span><span style=\"color: #000000\"> V): (x: T) </span><span style=\"color: #0000FF\">=&gt;</span><span style=\"color: #000000\"> V {</span>\n<span style=\"color: #000000\">    </span>\n<span style=\"color: #000000\">    </span><span style=\"color: #0000FF\">return</span><span style=\"color: #000000\"> x </span><span style=\"color: #0000FF\">=&gt;</span><span style=\"color: #000000\"> </span><span style=\"color: #0000FF\">new</span><span style=\"color: #000000\"> G(</span><span style=\"color: #0000FF\">new</span><span style=\"color: #000000\"> F(x))</span>\n<span style=\"color: #000000\">}</span>\n\n<span style=\"color: #0000FF\">let</span><span style=\"color: #000000\"> f = composeCtor(Box, Bag); </span><span style=\"color: #008000\">// has type '&lt;T&gt;(x: T) =&gt; Bag&lt;Box&lt;T&gt;&gt;'</span>\n<span style=\"color: #0000FF\">let</span><span style=\"color: #000000\"> a = f(</span><span style=\"color: #09835A\">1024</span><span style=\"color: #000000\">); </span><span style=\"color: #008000\">// has type 'Bag&lt;Box&lt;number&gt;&gt;'</span></code></div></pre>\n<p>In addition to compositional patterns like the above, this new inference on generic constructors means that functions that operate on class components in certain UI libraries like React can more correctly operate on generic class components.</p>\n<pre class=\"shiki\"><div class=\"language-id\">ts</div><div class='code-container'><code><span style=\"color: #0000FF\">type</span><span style=\"color: #000000\"> ComponentClass&lt;P&gt; = </span><span style=\"color: #0000FF\">new</span><span style=\"color: #000000\"> (props: P) </span><span style=\"color: #0000FF\">=&gt;</span><span style=\"color: #000000\"> Component&lt;P&gt;;</span>\n<span style=\"color: #0000FF\">declare</span><span style=\"color: #000000\"> </span><span style=\"color: #0000FF\">class</span><span style=\"color: #000000\"> Component&lt;P&gt; {</span>\n<span style=\"color: #000000\">    props: P;</span>\n<span style=\"color: #000000\">    </span><span style=\"color: #0000FF\">constructor</span><span style=\"color: #000000\">(props: P);</span>\n<span style=\"color: #000000\">}</span>\n\n<span style=\"color: #0000FF\">declare</span><span style=\"color: #000000\"> </span><span style=\"color: #0000FF\">function</span><span style=\"color: #000000\"> myHoc&lt;P&gt;(C: ComponentClass&lt;P&gt;): ComponentClass&lt;P&gt;;</span>\n\n<span style=\"color: #0000FF\">type</span><span style=\"color: #000000\"> NestedProps&lt;T&gt; = { foo: number, stuff: T };</span>\n\n<span style=\"color: #0000FF\">declare</span><span style=\"color: #000000\"> </span><span style=\"color: #0000FF\">class</span><span style=\"color: #000000\"> GenericComponent&lt;T&gt; </span><span style=\"color: #0000FF\">extends</span><span style=\"color: #000000\"> Component&lt;NestedProps&lt;T&gt;&gt; {</span>\n<span style=\"color: #000000\">}</span>\n\n<span style=\"color: #008000\">// type is 'new &lt;T&gt;(props: NestedProps&lt;T&gt;) =&gt; Component&lt;NestedProps&lt;T&gt;&gt;'</span>\n<span style=\"color: #0000FF\">const</span><span style=\"color: #000000\"> GenericComponent2 = myHoc(GenericComponent);</span></code></div></pre>\n<p>To learn more, <a href=\"https://github.com/microsoft/TypeScript/pull/31116\">check out the original pull request on GitHub</a>.</p>","headings":[{"value":"Speed improvements","depth":2},{"value":"Type-checking speed-ups","depth":3},{"value":"--incremental improvements","depth":3},{"value":"The Omit helper type","depth":2},{"value":"Improved excess property checks in union types","depth":3},{"value":"The --allowUmdGlobalAccess flag","depth":2},{"value":"Smarter union type checking","depth":2},{"value":"Higher order type inference from generic constructors","depth":2}],"frontmatter":{"permalink":"/docs/handbook/release-notes/typescript-3-5.html","title":"TypeScript 3.5"}}},"pageContext":{"slug":"/docs/handbook/release-notes/typescript-3-5.html","isOldHandbook":true}}}