From b6455a2566e0c7b9ecc44c6b521da08442e80b0d Mon Sep 17 00:00:00 2001 From: Matthew Brown Date: Wed, 28 Dec 2016 18:55:16 -0500 Subject: [PATCH] Improve how we disable clauses --- .../Checker/Statements/Block/IfChecker.php | 11 +++- tests/ScopeTest.php | 52 +++++++++++++++---- 2 files changed, 52 insertions(+), 11 deletions(-) diff --git a/src/Psalm/Checker/Statements/Block/IfChecker.php b/src/Psalm/Checker/Statements/Block/IfChecker.php index 7e514b4da..548fd0563 100644 --- a/src/Psalm/Checker/Statements/Block/IfChecker.php +++ b/src/Psalm/Checker/Statements/Block/IfChecker.php @@ -293,6 +293,10 @@ class IfChecker $statements_checker->getSuppressedIssues() ); + foreach ($changed_vars as $changed_var) { + $outer_context->removeVarFromClauses($changed_var); + } + if ($outer_context_vars_reconciled === false) { return false; } @@ -305,11 +309,16 @@ class IfChecker // We only update vars that changed both at the start of the if block and then again by an assignment // in the if statement. if ($if_scope->negated_types && !$mic_drop) { + $vars_to_update = array_intersect( + array_keys($pre_assignment_else_redefined_vars), + array_keys($if_scope->negated_types) + ); + $outer_context->update( $old_if_context, $if_context, $has_leaving_statements, - array_intersect(array_keys($pre_assignment_else_redefined_vars), array_keys($if_scope->negated_types)), + $vars_to_update, $if_scope->updated_vars ); } diff --git a/tests/ScopeTest.php b/tests/ScopeTest.php index 59afd2c73..e8cea7488 100644 --- a/tests/ScopeTest.php +++ b/tests/ScopeTest.php @@ -840,8 +840,8 @@ class ScopeTest extends PHPUnit_Framework_TestCase $a = rand(0, 10) ? "hello" : null; $b = rand(0, 10) ? "goodbye" : null; - if ($a || $b) { - if ($a) { + if ($a !== null || $b !== null) { + if ($a !== null) { $c = $a; } else { $c = $b; @@ -862,10 +862,10 @@ class ScopeTest extends PHPUnit_Framework_TestCase $b = rand(0, 10) ? "goodbye" : null; $c = rand(0, 10) ? "hello" : null; - if ($a || $b || $c) { - if ($a) { + if ($a !== null || $b !== null || $c !== null) { + if ($a !== null) { $d = $a; - } elseif ($b) { + } elseif ($b !== null) { $d = $b; } else { $d = $c; @@ -881,7 +881,7 @@ class ScopeTest extends PHPUnit_Framework_TestCase /** * @expectedException \Psalm\Exception\CodeException - * @expectedExceptionMessage InvalidScalarArgument + * @expectedExceptionMessage NullArgument */ public function testThreeVarLogicWithChange() { @@ -890,12 +890,44 @@ class ScopeTest extends PHPUnit_Framework_TestCase $b = rand(0, 10) ? "goodbye" : null; $c = rand(0, 10) ? "hello" : null; - if ($a || $b || $c) { - $c = false; + if ($a !== null || $b !== null || $c !== null) { + $c = null; - if ($a) { + if ($a !== null) { $d = $a; - } elseif ($b) { + } elseif ($b !== null) { + $d = $b; + } else { + $d = $c; + } + + echo strpos($d, "e"); + } + '); + + $file_checker = new FileChecker('somefile.php', $stmts); + $file_checker->check(); + } + + /** + * @expectedException \Psalm\Exception\CodeException + * @expectedExceptionMessage NullArgument + */ + public function testThreeVarLogicWithException() + { + $stmts = self::$parser->parse('