diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index da1af15dfa458..ac5733392e511 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -14925,6 +14925,9 @@ namespace ts { return type; } if (assumeTrue && !(type.flags & TypeFlags.Union)) { + if (type.flags & TypeFlags.Unknown && literal.text === "object") { + return getUnionType([nonPrimitiveType, nullType]); + } // We narrow a non-union type to an exact primitive type if the non-union type // is a supertype of that primitive type. For example, type 'any' can be narrowed // to one of the primitive types. diff --git a/tests/baselines/reference/narrowUnknownByTypeofObject.js b/tests/baselines/reference/narrowUnknownByTypeofObject.js new file mode 100644 index 0000000000000..076d91e0df8e5 --- /dev/null +++ b/tests/baselines/reference/narrowUnknownByTypeofObject.js @@ -0,0 +1,14 @@ +//// [narrowUnknownByTypeofObject.ts] +function foo(x: unknown) { + if (typeof x === "object") { + x + } +} + + +//// [narrowUnknownByTypeofObject.js] +function foo(x) { + if (typeof x === "object") { + x; + } +} diff --git a/tests/baselines/reference/narrowUnknownByTypeofObject.symbols b/tests/baselines/reference/narrowUnknownByTypeofObject.symbols new file mode 100644 index 0000000000000..ee3ec77ec04d9 --- /dev/null +++ b/tests/baselines/reference/narrowUnknownByTypeofObject.symbols @@ -0,0 +1,13 @@ +=== tests/cases/compiler/narrowUnknownByTypeofObject.ts === +function foo(x: unknown) { +>foo : Symbol(foo, Decl(narrowUnknownByTypeofObject.ts, 0, 0)) +>x : Symbol(x, Decl(narrowUnknownByTypeofObject.ts, 0, 13)) + + if (typeof x === "object") { +>x : Symbol(x, Decl(narrowUnknownByTypeofObject.ts, 0, 13)) + + x +>x : Symbol(x, Decl(narrowUnknownByTypeofObject.ts, 0, 13)) + } +} + diff --git a/tests/baselines/reference/narrowUnknownByTypeofObject.types b/tests/baselines/reference/narrowUnknownByTypeofObject.types new file mode 100644 index 0000000000000..98225861d1e0b --- /dev/null +++ b/tests/baselines/reference/narrowUnknownByTypeofObject.types @@ -0,0 +1,16 @@ +=== tests/cases/compiler/narrowUnknownByTypeofObject.ts === +function foo(x: unknown) { +>foo : (x: unknown) => void +>x : unknown + + if (typeof x === "object") { +>typeof x === "object" : boolean +>typeof x : "string" | "number" | "boolean" | "symbol" | "undefined" | "object" | "function" +>x : unknown +>"object" : "object" + + x +>x : object | null + } +} + diff --git a/tests/cases/compiler/narrowUnknownByTypeofObject.ts b/tests/cases/compiler/narrowUnknownByTypeofObject.ts new file mode 100644 index 0000000000000..36e1c18f4f670 --- /dev/null +++ b/tests/cases/compiler/narrowUnknownByTypeofObject.ts @@ -0,0 +1,6 @@ +// @strictNullChecks: true +function foo(x: unknown) { + if (typeof x === "object") { + x + } +}