Skip to content

Conversation

@john-shaffer
Copy link
Contributor

@john-shaffer john-shaffer commented Oct 21, 2025

Removes ifs, elseifs, and elses with no body. Combines them with others when appropriate.

class RemoveDeadIfBlock
{
    public function run($condition)
    {
-        if ($value) {
-        } elseif ($differentValue) {
-        if ($differentValue) {
-        } else {
-        }
-
        if ($differentValue) {
            echo 'different';
-        } elseif ($value) {
-        } else {
        }

-        if ($differentValue) {
-        } elseif ($value) {
+        if (!$differentValue && $value) {
            echo 'value';
-        } else {
        }

        return $differentValue;
    }
}

We avoid merging if into following conditions when the if itself has a comment, because we can't tell if the comment will still be correct for the negated condition.

At first, I tried adding logic to RemoveDeadIfForeachForRector to remove elseifs and elses. That worked, but as I added code it was clunky to have so much unrelated if logic in a for and foreach rector. So I moved it to a brand new rector with a simpler implementation. I borrowed significant code from RemoveAlwaysTrueIfConditionRector as well.

This can serve as support for smarter rectors like "RemoveAlwaysTrueIf" and my WIP "RemoveAlwaysFalseIf". Properly modifying ifs requires a lot of extra logic that complicates the implementation of those rectors. In the future, they can do something simpler like removing the body statements but leaving the if structure in place. Then this rector can perform the restructuring of the if.

Removes ifs, elseifs, and elses with no body.
Combines them with others when appropriate.

```diff
class RemoveDeadIfBlock
{
    public function run($condition)
    {
-        if ($value) {
-        } elseif ($differentValue) {
-        if ($differentValue) {
-        } else {
-        }
-
        if ($differentValue) {
            echo 'different';
-        } elseif ($value) {
-        } else {
        }

-        if ($differentValue) {
-        } elseif ($value) {
+        if (!$differentValue && $value) {
            echo 'value';
        } else {
        }

        return $differentValue;
    }
}
```

We avoid merging `if`` into following conditions
when the `if` itself has a comment, because we
can't tell if the comment will still be correct for
the negated condition.

At first, I tried adding logic to
RemoveDeadIfForeachForRector to remove elseifs
and elses. That worked, but as I added code it
was clunky to have so much unrelated `if` logic
in `for` and `foreach` rector. So I moved it to
a brand new rector with a simpler implementation.
I borrowed significant code from
RemoveAlwaysTrueIfConditionRector as well.

This can serve as support for smarter rectors
like "RemoveAlwaysTrueIf" and my WIP
"RemoveAlwaysFalseIf". Properly modifying `if`s
requires a lot of extra logic that complicates
the implementation of those rectors. In the
future, they can do something simpler like
removing the body statements but leaving the if
structure in place. Then this rector can perform
the restructuring of the if.
I accidentally put an && ! condition rather than
an ||, causing elseifs with skippable exprs to get
removed rather than being skipped.

- Fix the conditional
- Add a test for skippable exprs in elseif
  condition.
@john-shaffer john-shaffer force-pushed the add-remove-dead-if-blocks-rector branch from 3e2a8d0 to 13e2191 Compare October 21, 2025 19:14
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants