diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts
index 9831899a1b2c0..3736179db54b0 100644
--- a/src/compiler/checker.ts
+++ b/src/compiler/checker.ts
@@ -27929,10 +27929,10 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
if (isMatchingConstructorReference(right)) {
return narrowTypeByConstructor(type, operator, left, assumeTrue);
}
- if (isBooleanLiteral(right)) {
+ if (isBooleanLiteral(right) && !isAccessExpression(left)) {
return narrowTypeByBooleanComparison(type, left, right, operator, assumeTrue);
}
- if (isBooleanLiteral(left)) {
+ if (isBooleanLiteral(left) && !isAccessExpression(right)) {
return narrowTypeByBooleanComparison(type, right, left, operator, assumeTrue);
}
break;
diff --git a/tests/baselines/reference/controlFlowOptionalChain3.errors.txt b/tests/baselines/reference/controlFlowOptionalChain3.errors.txt
new file mode 100644
index 0000000000000..15a8997f0376e
--- /dev/null
+++ b/tests/baselines/reference/controlFlowOptionalChain3.errors.txt
@@ -0,0 +1,49 @@
+controlFlowOptionalChain3.tsx(30,8): error TS18048: 'foo' is possibly 'undefined'.
+controlFlowOptionalChain3.tsx(36,31): error TS18048: 'options' is possibly 'undefined'.
+
+
+==== controlFlowOptionalChain3.tsx (2 errors) ====
+ ///
+
+ // https://github.com/microsoft/TypeScript/issues/56482
+
+ import React from "react";
+
+ interface Foo {
+ bar: boolean;
+ }
+
+ function test1(foo: Foo | undefined) {
+ if (foo?.bar === false) {
+ foo;
+ }
+ foo;
+ }
+
+ function test2(foo: Foo | undefined) {
+ if (foo?.bar === false) {
+ foo;
+ } else {
+ foo;
+ }
+ }
+
+ function Test3({ foo }: { foo: Foo | undefined }) {
+ return (
+
+ {foo?.bar === false && "foo"}
+ {foo.bar ? "true" : "false"}
+ ~~~
+!!! error TS18048: 'foo' is possibly 'undefined'.
+
+ );
+ }
+
+ function test4(options?: { a?: boolean; b?: boolean }) {
+ if (options?.a === false || options.b) {
+ ~~~~~~~
+!!! error TS18048: 'options' is possibly 'undefined'.
+ options;
+ }
+ }
+
\ No newline at end of file
diff --git a/tests/baselines/reference/controlFlowOptionalChain3.symbols b/tests/baselines/reference/controlFlowOptionalChain3.symbols
new file mode 100644
index 0000000000000..714e32bd6e1ee
--- /dev/null
+++ b/tests/baselines/reference/controlFlowOptionalChain3.symbols
@@ -0,0 +1,98 @@
+//// [tests/cases/conformance/controlFlow/controlFlowOptionalChain3.tsx] ////
+
+=== controlFlowOptionalChain3.tsx ===
+///
+
+// https://github.com/microsoft/TypeScript/issues/56482
+
+import React from "react";
+>React : Symbol(React, Decl(controlFlowOptionalChain3.tsx, 4, 6))
+
+interface Foo {
+>Foo : Symbol(Foo, Decl(controlFlowOptionalChain3.tsx, 4, 26))
+
+ bar: boolean;
+>bar : Symbol(Foo.bar, Decl(controlFlowOptionalChain3.tsx, 6, 15))
+}
+
+function test1(foo: Foo | undefined) {
+>test1 : Symbol(test1, Decl(controlFlowOptionalChain3.tsx, 8, 1))
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 10, 15))
+>Foo : Symbol(Foo, Decl(controlFlowOptionalChain3.tsx, 4, 26))
+
+ if (foo?.bar === false) {
+>foo?.bar : Symbol(Foo.bar, Decl(controlFlowOptionalChain3.tsx, 6, 15))
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 10, 15))
+>bar : Symbol(Foo.bar, Decl(controlFlowOptionalChain3.tsx, 6, 15))
+
+ foo;
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 10, 15))
+ }
+ foo;
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 10, 15))
+}
+
+function test2(foo: Foo | undefined) {
+>test2 : Symbol(test2, Decl(controlFlowOptionalChain3.tsx, 15, 1))
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 17, 15))
+>Foo : Symbol(Foo, Decl(controlFlowOptionalChain3.tsx, 4, 26))
+
+ if (foo?.bar === false) {
+>foo?.bar : Symbol(Foo.bar, Decl(controlFlowOptionalChain3.tsx, 6, 15))
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 17, 15))
+>bar : Symbol(Foo.bar, Decl(controlFlowOptionalChain3.tsx, 6, 15))
+
+ foo;
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 17, 15))
+
+ } else {
+ foo;
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 17, 15))
+ }
+}
+
+function Test3({ foo }: { foo: Foo | undefined }) {
+>Test3 : Symbol(Test3, Decl(controlFlowOptionalChain3.tsx, 23, 1))
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 25, 16))
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 25, 25))
+>Foo : Symbol(Foo, Decl(controlFlowOptionalChain3.tsx, 4, 26))
+
+ return (
+
+>div : Symbol(JSX.IntrinsicElements.div, Decl(react16.d.ts, 2546, 114))
+
+ {foo?.bar === false && "foo"}
+>foo?.bar : Symbol(Foo.bar, Decl(controlFlowOptionalChain3.tsx, 6, 15))
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 25, 16))
+>bar : Symbol(Foo.bar, Decl(controlFlowOptionalChain3.tsx, 6, 15))
+
+ {foo.bar ? "true" : "false"}
+>foo.bar : Symbol(Foo.bar, Decl(controlFlowOptionalChain3.tsx, 6, 15))
+>foo : Symbol(foo, Decl(controlFlowOptionalChain3.tsx, 25, 16))
+>bar : Symbol(Foo.bar, Decl(controlFlowOptionalChain3.tsx, 6, 15))
+
+
+>div : Symbol(JSX.IntrinsicElements.div, Decl(react16.d.ts, 2546, 114))
+
+ );
+}
+
+function test4(options?: { a?: boolean; b?: boolean }) {
+>test4 : Symbol(test4, Decl(controlFlowOptionalChain3.tsx, 32, 1))
+>options : Symbol(options, Decl(controlFlowOptionalChain3.tsx, 34, 15))
+>a : Symbol(a, Decl(controlFlowOptionalChain3.tsx, 34, 26))
+>b : Symbol(b, Decl(controlFlowOptionalChain3.tsx, 34, 39))
+
+ if (options?.a === false || options.b) {
+>options?.a : Symbol(a, Decl(controlFlowOptionalChain3.tsx, 34, 26))
+>options : Symbol(options, Decl(controlFlowOptionalChain3.tsx, 34, 15))
+>a : Symbol(a, Decl(controlFlowOptionalChain3.tsx, 34, 26))
+>options.b : Symbol(b, Decl(controlFlowOptionalChain3.tsx, 34, 39))
+>options : Symbol(options, Decl(controlFlowOptionalChain3.tsx, 34, 15))
+>b : Symbol(b, Decl(controlFlowOptionalChain3.tsx, 34, 39))
+
+ options;
+>options : Symbol(options, Decl(controlFlowOptionalChain3.tsx, 34, 15))
+ }
+}
+
diff --git a/tests/baselines/reference/controlFlowOptionalChain3.types b/tests/baselines/reference/controlFlowOptionalChain3.types
new file mode 100644
index 0000000000000..2ef7dc502c01a
--- /dev/null
+++ b/tests/baselines/reference/controlFlowOptionalChain3.types
@@ -0,0 +1,110 @@
+//// [tests/cases/conformance/controlFlow/controlFlowOptionalChain3.tsx] ////
+
+=== controlFlowOptionalChain3.tsx ===
+///
+
+// https://github.com/microsoft/TypeScript/issues/56482
+
+import React from "react";
+>React : typeof React
+
+interface Foo {
+ bar: boolean;
+>bar : boolean
+}
+
+function test1(foo: Foo | undefined) {
+>test1 : (foo: Foo | undefined) => void
+>foo : Foo | undefined
+
+ if (foo?.bar === false) {
+>foo?.bar === false : boolean
+>foo?.bar : boolean | undefined
+>foo : Foo | undefined
+>bar : boolean | undefined
+>false : false
+
+ foo;
+>foo : Foo
+ }
+ foo;
+>foo : Foo | undefined
+}
+
+function test2(foo: Foo | undefined) {
+>test2 : (foo: Foo | undefined) => void
+>foo : Foo | undefined
+
+ if (foo?.bar === false) {
+>foo?.bar === false : boolean
+>foo?.bar : boolean | undefined
+>foo : Foo | undefined
+>bar : boolean | undefined
+>false : false
+
+ foo;
+>foo : Foo
+
+ } else {
+ foo;
+>foo : Foo | undefined
+ }
+}
+
+function Test3({ foo }: { foo: Foo | undefined }) {
+>Test3 : ({ foo }: { foo: Foo | undefined; }) => JSX.Element
+>foo : Foo | undefined
+>foo : Foo | undefined
+
+ return (
+>( {foo?.bar === false && "foo"} {foo.bar ? "true" : "false"}
) : JSX.Element
+
+
+>
{foo?.bar === false && "foo"} {foo.bar ? "true" : "false"}
: JSX.Element
+>div : any
+
+ {foo?.bar === false && "foo"}
+>foo?.bar === false && "foo" : false | "foo"
+>foo?.bar === false : boolean
+>foo?.bar : boolean | undefined
+>foo : Foo | undefined
+>bar : boolean | undefined
+>false : false
+>"foo" : "foo"
+
+ {foo.bar ? "true" : "false"}
+>foo.bar ? "true" : "false" : "false" | "true"
+>foo.bar : boolean
+>foo : Foo | undefined
+>bar : boolean
+>"true" : "true"
+>"false" : "false"
+
+
+>div : any
+
+ );
+}
+
+function test4(options?: { a?: boolean; b?: boolean }) {
+>test4 : (options?: { a?: boolean; b?: boolean;}) => void
+>options : { a?: boolean | undefined; b?: boolean | undefined; } | undefined
+>a : boolean | undefined
+>b : boolean | undefined
+
+ if (options?.a === false || options.b) {
+>options?.a === false || options.b : boolean | undefined
+>options?.a === false : boolean
+>options?.a : boolean | undefined
+>options : { a?: boolean | undefined; b?: boolean | undefined; } | undefined
+>a : boolean | undefined
+>false : false
+>options.b : boolean | undefined
+>options : { a?: boolean | undefined; b?: boolean | undefined; } | undefined
+>b : boolean | undefined
+
+ options;
+>options : { a?: boolean | undefined; b?: boolean | undefined; } | undefined
+ }
+}
+
diff --git a/tests/cases/conformance/controlFlow/controlFlowOptionalChain3.tsx b/tests/cases/conformance/controlFlow/controlFlowOptionalChain3.tsx
new file mode 100644
index 0000000000000..191de7ed68255
--- /dev/null
+++ b/tests/cases/conformance/controlFlow/controlFlowOptionalChain3.tsx
@@ -0,0 +1,44 @@
+// @strict: true
+// @noEmit: true
+// @esModuleInterop: true
+// @jsx: react
+
+///
+
+// https://github.com/microsoft/TypeScript/issues/56482
+
+import React from "react";
+
+interface Foo {
+ bar: boolean;
+}
+
+function test1(foo: Foo | undefined) {
+ if (foo?.bar === false) {
+ foo;
+ }
+ foo;
+}
+
+function test2(foo: Foo | undefined) {
+ if (foo?.bar === false) {
+ foo;
+ } else {
+ foo;
+ }
+}
+
+function Test3({ foo }: { foo: Foo | undefined }) {
+ return (
+
+ {foo?.bar === false && "foo"}
+ {foo.bar ? "true" : "false"}
+
+ );
+}
+
+function test4(options?: { a?: boolean; b?: boolean }) {
+ if (options?.a === false || options.b) {
+ options;
+ }
+}