rector icon indicating copy to clipboard operation
rector copied to clipboard

[php 8.4] Add array_find function upgrade rule

Open TomasVotruba opened this issue 9 months ago • 1 comments

$animals = ['dog', 'cat', 'cow', 'duck', 'goose'];
-$found = null;
-foreach ($animals as $animal) {
-    if (str_starts_with($animal, 'c')) {
-        $found = $animal;
-        break;
-    }
-}
+$found = array_find($animals, fn($animal) => str_starts_with($animal, 'c'));

TomasVotruba avatar May 06 '25 13:05 TomasVotruba

There are other functions that exist in php 8.4:

  • array_any
  • array_all

samsonasik avatar May 12 '25 09:05 samsonasik

array_find - https://github.com/rectorphp/rector-src/pull/7009 array_find_key - https://github.com/rectorphp/rector-src/pull/7008 array_any - https://github.com/rectorphp/rector-src/pull/7010 array_all - https://github.com/rectorphp/rector-src/pull/7011

Let me know if you need changes with either.

xHeaven avatar Jun 21 '25 18:06 xHeaven

Downgrade rule(s) is needed for this so new transformed to php 8.4 array_ code can be downgraded

https://github.com/rectorphp/rector-downgrade-php

samsonasik avatar Jun 21 '25 22:06 samsonasik

Downgrade rule(s) is needed for this so new transformed to php 8.4 array_ code can be downgraded

rectorphp/rector-downgrade-php

I didn't even know this existed - I might file a PR with the changes. 👀

xHeaven avatar Jun 21 '25 23:06 xHeaven

Awesome, after rule created, register to downgrade config set https://github.com/rectorphp/rector-downgrade-php/blob/main/config/set/downgrade-php84.php

samsonasik avatar Jun 21 '25 23:06 samsonasik

ForeachToArrayFindKeyRector replaces code using iterable objects (instead of arrays).

$animals = new \ArrayIterator(['dog', 'cat', 'cow', 'duck', 'goose']);

$found = null;
foreach ($animals as $idx => $animal) {
    if (str_starts_with($animal, 'c')) {
        $found = $idx;
        break;
    }
}

is replaced by:

$animals = new \ArrayIterator(['dog', 'cat', 'cow', 'duck', 'goose']);
$found = array_find_key($animals, fn($animal) => str_starts_with($animal, 'c'));

which is invalid, because array_find_key only supports arrays.

Did not check the other rules.

(Note that it is not reproducible on getrector.com. But the example from ForeachToArrayFindKeyRector.com is also not working there).

gharlan avatar Jun 26 '25 15:06 gharlan

@gharlan php version 80400 need to be set on demo page to be able to reproduce https://getrector.com/demo/89a7b249-f374-4868-b328-30a883b833be

samsonasik avatar Jun 26 '25 16:06 samsonasik

@gharlan I created PR:

  • https://github.com/rectorphp/rector-src/pull/7023

for that to skip non-array.

samsonasik avatar Jun 26 '25 16:06 samsonasik

Nice catch @gharlan, I completely forgot about the existence of iterables. Oh well. Thanks @samsonasik for the quick fix!

xHeaven avatar Jun 26 '25 16:06 xHeaven

Thanks everyone for quick work 💪

TomasVotruba avatar Jun 26 '25 16:06 TomasVotruba

@TomasVotruba the downgrade rules still needed, I think this can be re-open to avoid user upgrade to php 8.4, and can't downgrade to php < 8.4

samsonasik avatar Jun 26 '25 16:06 samsonasik

This issue has been automatically locked because it has been closed for 150 days. Please open a new issue if you have a similar problem.

github-actions[bot] avatar Nov 28 '25 03:11 github-actions[bot]