mirror of
https://github.com/rectorphp/rector.git
synced 2024-06-26 12:52:36 +00:00
[TASK] Add FunctionArgumentDefaultValueReplacerRector (#63)
This commit is contained in:
parent
eb82c401dd
commit
e961ed1750
|
@ -3,7 +3,9 @@
|
|||
declare(strict_types=1);
|
||||
|
||||
use Rector\Arguments\Rector\ClassMethod\ArgumentAdderRector;
|
||||
use Rector\Arguments\Rector\FuncCall\FunctionArgumentDefaultValueReplacerRector;
|
||||
use Rector\Arguments\ValueObject\ArgumentAdder;
|
||||
use Rector\Arguments\ValueObject\FuncCallArgumentDefaultValueReplacer;
|
||||
use Rector\DeadCode\Rector\StaticCall\RemoveParentCallWithoutParentRector;
|
||||
use Rector\Php80\Rector\Catch_\RemoveUnusedVariableInCatchRector;
|
||||
use Rector\Php80\Rector\Class_\ClassPropertyAssignToConstructorPromotionRector;
|
||||
|
@ -91,4 +93,19 @@ return static function (ContainerConfigurator $containerConfigurator): void {
|
|||
],
|
||||
]]);
|
||||
$services->set(OptionalParametersAfterRequiredRector::class);
|
||||
|
||||
$services->set(Rector\Arguments\Rector\FuncCall\FunctionArgumentDefaultValueReplacerRector::class)
|
||||
->call('configure', [[
|
||||
FunctionArgumentDefaultValueReplacerRector::REPLACED_ARGUMENTS => ValueObjectInliner::inline([
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, 'gte', 'ge'),
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, 'lte', 'le'),
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, '', '!='),
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, '!', '!='),
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, 'g', 'gt'),
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, 'l', 'lt'),
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, 'gte', 'ge'),
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, 'lte', 'le'),
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, 'n', 'ne'),
|
||||
]),
|
||||
]]);
|
||||
};
|
||||
|
|
|
@ -0,0 +1,27 @@
|
|||
<?php
|
||||
|
||||
namespace Rector\Tests\Arguments\Rector\FuncCall\FunctionArgumentDefaultValueReplacerRector\Fixture;
|
||||
|
||||
class SomeClass
|
||||
{
|
||||
public function run()
|
||||
{
|
||||
some_function(true);
|
||||
}
|
||||
}
|
||||
|
||||
?>
|
||||
-----
|
||||
<?php
|
||||
|
||||
namespace Rector\Tests\Arguments\Rector\FuncCall\FunctionArgumentDefaultValueReplacerRector\Fixture;
|
||||
|
||||
class SomeClass
|
||||
{
|
||||
public function run()
|
||||
{
|
||||
some_function(\Symfony\Component\Yaml\Yaml::DUMP_EXCEPTION_ON_INVALID_TYPE);
|
||||
}
|
||||
}
|
||||
|
||||
?>
|
|
@ -0,0 +1,33 @@
|
|||
<?php
|
||||
|
||||
namespace Rector\Tests\Arguments\Rector\FuncCall\FunctionArgumentDefaultValueReplacerRector\Fixture;
|
||||
|
||||
class VersionCompare
|
||||
{
|
||||
public function run()
|
||||
{
|
||||
version_compare(1, 2);
|
||||
version_compare(1, 2, '');
|
||||
version_compare(PHP_VERSION, '5.6', 'lte');
|
||||
version_compare(PHP_VERSION, '5.6', 'le');
|
||||
}
|
||||
}
|
||||
|
||||
?>
|
||||
-----
|
||||
<?php
|
||||
|
||||
namespace Rector\Tests\Arguments\Rector\FuncCall\FunctionArgumentDefaultValueReplacerRector\Fixture;
|
||||
|
||||
class VersionCompare
|
||||
{
|
||||
public function run()
|
||||
{
|
||||
version_compare(1, 2);
|
||||
version_compare(1, 2, '!=');
|
||||
version_compare(PHP_VERSION, '5.6', 'le');
|
||||
version_compare(PHP_VERSION, '5.6', 'le');
|
||||
}
|
||||
}
|
||||
|
||||
?>
|
|
@ -0,0 +1,33 @@
|
|||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Rector\Tests\Arguments\Rector\FuncCall\FunctionArgumentDefaultValueReplacerRector;
|
||||
|
||||
use Iterator;
|
||||
use Rector\Testing\PHPUnit\AbstractRectorTestCase;
|
||||
use Symplify\SmartFileSystem\SmartFileInfo;
|
||||
|
||||
final class FunctionArgumentDefaultValueReplacerRectorTest extends AbstractRectorTestCase
|
||||
{
|
||||
/**
|
||||
* @dataProvider provideData()
|
||||
*/
|
||||
public function test(SmartFileInfo $fileInfo): void
|
||||
{
|
||||
$this->doTestFileInfo($fileInfo);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return Iterator<SmartFileInfo>
|
||||
*/
|
||||
public function provideData(): Iterator
|
||||
{
|
||||
return $this->yieldFilesFromDirectory(__DIR__ . '/Fixture');
|
||||
}
|
||||
|
||||
public function provideConfigFilePath(): string
|
||||
{
|
||||
return __DIR__ . '/config/configured_rule.php';
|
||||
}
|
||||
}
|
|
@ -0,0 +1,25 @@
|
|||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
use Rector\Arguments\Rector\FuncCall\FunctionArgumentDefaultValueReplacerRector;
|
||||
use Rector\Arguments\ValueObject\FuncCallArgumentDefaultValueReplacer;
|
||||
use Symfony\Component\DependencyInjection\Loader\Configurator\ContainerConfigurator;
|
||||
use Symplify\SymfonyPhpConfig\ValueObjectInliner;
|
||||
|
||||
return static function (ContainerConfigurator $containerConfigurator): void {
|
||||
$services = $containerConfigurator->services();
|
||||
$services->set(Rector\Arguments\Rector\FuncCall\FunctionArgumentDefaultValueReplacerRector::class)
|
||||
->call('configure', [[
|
||||
FunctionArgumentDefaultValueReplacerRector::REPLACED_ARGUMENTS => ValueObjectInliner::inline([
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, 'lte', 'le'),
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, '', '!='),
|
||||
new FuncCallArgumentDefaultValueReplacer(
|
||||
'some_function',
|
||||
0,
|
||||
true,
|
||||
'Symfony\Component\Yaml\Yaml::DUMP_EXCEPTION_ON_INVALID_TYPE'
|
||||
),
|
||||
]),
|
||||
]]);
|
||||
};
|
137
rules/Arguments/ArgumentDefaultValueReplacer.php
Normal file
137
rules/Arguments/ArgumentDefaultValueReplacer.php
Normal file
|
@ -0,0 +1,137 @@
|
|||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Rector\Arguments;
|
||||
|
||||
use Nette\Utils\Strings;
|
||||
use PhpParser\BuilderHelpers;
|
||||
use PhpParser\Node;
|
||||
use PhpParser\Node\Arg;
|
||||
use PhpParser\Node\Expr;
|
||||
use PhpParser\Node\Expr\FuncCall;
|
||||
use PhpParser\Node\Expr\MethodCall;
|
||||
use PhpParser\Node\Expr\StaticCall;
|
||||
use PhpParser\Node\Stmt\ClassMethod;
|
||||
use Rector\Arguments\Contract\ArgumentDefaultValueReplacerInterface;
|
||||
use Rector\Core\PhpParser\Node\NodeFactory;
|
||||
use Rector\Core\PhpParser\Node\Value\ValueResolver;
|
||||
|
||||
final class ArgumentDefaultValueReplacer
|
||||
{
|
||||
public function __construct(
|
||||
private NodeFactory $nodeFactory,
|
||||
private ValueResolver $valueResolver
|
||||
) {
|
||||
}
|
||||
|
||||
/**
|
||||
* @param MethodCall|StaticCall|ClassMethod|Expr\FuncCall $node
|
||||
*/
|
||||
public function processReplaces(
|
||||
Node $node,
|
||||
ArgumentDefaultValueReplacerInterface $argumentDefaultValueReplacer
|
||||
): ?Node {
|
||||
if ($node instanceof ClassMethod) {
|
||||
if (! isset($node->params[$argumentDefaultValueReplacer->getPosition()])) {
|
||||
return null;
|
||||
}
|
||||
} elseif (isset($node->args[$argumentDefaultValueReplacer->getPosition()])) {
|
||||
$this->processArgs($node, $argumentDefaultValueReplacer);
|
||||
}
|
||||
|
||||
return $node;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param MethodCall|StaticCall|FuncCall $expr
|
||||
*/
|
||||
private function processArgs(Expr $expr, ArgumentDefaultValueReplacerInterface $argumentDefaultValueReplacer): void
|
||||
{
|
||||
$position = $argumentDefaultValueReplacer->getPosition();
|
||||
|
||||
$argValue = $this->valueResolver->getValue($expr->args[$position]->value);
|
||||
|
||||
if (is_scalar(
|
||||
$argumentDefaultValueReplacer->getValueBefore()
|
||||
) && $argValue === $argumentDefaultValueReplacer->getValueBefore()) {
|
||||
$expr->args[$position] = $this->normalizeValueToArgument($argumentDefaultValueReplacer->getValueAfter());
|
||||
} elseif (is_array($argumentDefaultValueReplacer->getValueBefore())) {
|
||||
$newArgs = $this->processArrayReplacement($expr->args, $argumentDefaultValueReplacer);
|
||||
|
||||
if ($newArgs) {
|
||||
$expr->args = $newArgs;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param mixed $value
|
||||
*/
|
||||
private function normalizeValueToArgument($value): Arg
|
||||
{
|
||||
// class constants → turn string to composite
|
||||
if (is_string($value) && Strings::contains($value, '::')) {
|
||||
[$class, $constant] = explode('::', $value);
|
||||
$classConstFetch = $this->nodeFactory->createClassConstFetch($class, $constant);
|
||||
|
||||
return new Arg($classConstFetch);
|
||||
}
|
||||
|
||||
return new Arg(BuilderHelpers::normalizeValue($value));
|
||||
}
|
||||
|
||||
/**
|
||||
* @param Arg[] $argumentNodes
|
||||
* @return Arg[]|null
|
||||
*/
|
||||
private function processArrayReplacement(
|
||||
array $argumentNodes,
|
||||
ArgumentDefaultValueReplacerInterface $argumentDefaultValueReplacer
|
||||
): ?array {
|
||||
$argumentValues = $this->resolveArgumentValuesToBeforeRecipe($argumentNodes, $argumentDefaultValueReplacer);
|
||||
if ($argumentValues !== $argumentDefaultValueReplacer->getValueBefore()) {
|
||||
return null;
|
||||
}
|
||||
|
||||
if (is_string($argumentDefaultValueReplacer->getValueAfter())) {
|
||||
$argumentNodes[$argumentDefaultValueReplacer->getPosition()] = $this->normalizeValueToArgument(
|
||||
$argumentDefaultValueReplacer->getValueAfter()
|
||||
);
|
||||
|
||||
// clear following arguments
|
||||
$argumentCountToClear = count($argumentDefaultValueReplacer->getValueBefore());
|
||||
for ($i = $argumentDefaultValueReplacer->getPosition() + 1; $i <= $argumentDefaultValueReplacer->getPosition() + $argumentCountToClear; ++$i) {
|
||||
unset($argumentNodes[$i]);
|
||||
}
|
||||
}
|
||||
|
||||
return $argumentNodes;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param Arg[] $argumentNodes
|
||||
* @return mixed[]
|
||||
*/
|
||||
private function resolveArgumentValuesToBeforeRecipe(
|
||||
array $argumentNodes,
|
||||
ArgumentDefaultValueReplacerInterface $argumentDefaultValueReplacer
|
||||
): array {
|
||||
$argumentValues = [];
|
||||
|
||||
/** @var mixed[] $valueBefore */
|
||||
$valueBefore = $argumentDefaultValueReplacer->getValueBefore();
|
||||
$beforeArgumentCount = count($valueBefore);
|
||||
|
||||
for ($i = 0; $i < $beforeArgumentCount; ++$i) {
|
||||
if (! isset($argumentNodes[$argumentDefaultValueReplacer->getPosition() + $i])) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$nextArg = $argumentNodes[$argumentDefaultValueReplacer->getPosition() + $i];
|
||||
$argumentValues[] = $this->valueResolver->getValue($nextArg->value);
|
||||
}
|
||||
|
||||
return $argumentValues;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,18 @@
|
|||
<?php
|
||||
|
||||
namespace Rector\Arguments\Contract;
|
||||
|
||||
interface ArgumentDefaultValueReplacerInterface
|
||||
{
|
||||
public function getPosition(): int;
|
||||
|
||||
/**
|
||||
* @return mixed
|
||||
*/
|
||||
public function getValueBefore();
|
||||
|
||||
/**
|
||||
* @return mixed
|
||||
*/
|
||||
public function getValueAfter();
|
||||
}
|
|
@ -4,11 +4,7 @@ declare(strict_types=1);
|
|||
|
||||
namespace Rector\Arguments\Rector\ClassMethod;
|
||||
|
||||
use Nette\Utils\Strings;
|
||||
use PhpParser\BuilderHelpers;
|
||||
use PhpParser\Node;
|
||||
use PhpParser\Node\Arg;
|
||||
use PhpParser\Node\Expr;
|
||||
use PhpParser\Node\Expr\MethodCall;
|
||||
use PhpParser\Node\Expr\StaticCall;
|
||||
use PhpParser\Node\Stmt\ClassMethod;
|
||||
|
@ -34,6 +30,11 @@ final class ArgumentDefaultValueReplacerRector extends AbstractRector implements
|
|||
*/
|
||||
private array $replacedArguments = [];
|
||||
|
||||
public function __construct(
|
||||
private \Rector\Arguments\ArgumentDefaultValueReplacer $argumentDefaultValueReplacer
|
||||
) {
|
||||
}
|
||||
|
||||
public function getRuleDefinition(): RuleDefinition
|
||||
{
|
||||
return new RuleDefinition(
|
||||
|
@ -91,7 +92,7 @@ CODE_SAMPLE
|
|||
continue;
|
||||
}
|
||||
|
||||
$this->processReplaces($node, $replacedArgument);
|
||||
$this->argumentDefaultValueReplacer->processReplaces($node, $replacedArgument);
|
||||
}
|
||||
|
||||
return $node;
|
||||
|
@ -106,112 +107,4 @@ CODE_SAMPLE
|
|||
Assert::allIsInstanceOf($replacedArguments, ArgumentDefaultValueReplacer::class);
|
||||
$this->replacedArguments = $replacedArguments;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param MethodCall|StaticCall|ClassMethod $node
|
||||
*/
|
||||
private function processReplaces(Node $node, ArgumentDefaultValueReplacer $argumentDefaultValueReplacer): ?Node
|
||||
{
|
||||
if ($node instanceof ClassMethod) {
|
||||
if (! isset($node->params[$argumentDefaultValueReplacer->getPosition()])) {
|
||||
return null;
|
||||
}
|
||||
} elseif (isset($node->args[$argumentDefaultValueReplacer->getPosition()])) {
|
||||
$this->processArgs($node, $argumentDefaultValueReplacer);
|
||||
}
|
||||
|
||||
return $node;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param MethodCall|StaticCall $expr
|
||||
*/
|
||||
private function processArgs(Expr $expr, ArgumentDefaultValueReplacer $argumentDefaultValueReplacer): void
|
||||
{
|
||||
$position = $argumentDefaultValueReplacer->getPosition();
|
||||
|
||||
$argValue = $this->valueResolver->getValue($expr->args[$position]->value);
|
||||
|
||||
if (is_scalar(
|
||||
$argumentDefaultValueReplacer->getValueBefore()
|
||||
) && $argValue === $argumentDefaultValueReplacer->getValueBefore()) {
|
||||
$expr->args[$position] = $this->normalizeValueToArgument($argumentDefaultValueReplacer->getValueAfter());
|
||||
} elseif (is_array($argumentDefaultValueReplacer->getValueBefore())) {
|
||||
$newArgs = $this->processArrayReplacement($expr->args, $argumentDefaultValueReplacer);
|
||||
|
||||
if ($newArgs) {
|
||||
$expr->args = $newArgs;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param mixed $value
|
||||
*/
|
||||
private function normalizeValueToArgument($value): Arg
|
||||
{
|
||||
// class constants → turn string to composite
|
||||
if (is_string($value) && Strings::contains($value, '::')) {
|
||||
[$class, $constant] = explode('::', $value);
|
||||
$classConstFetch = $this->nodeFactory->createClassConstFetch($class, $constant);
|
||||
|
||||
return new Arg($classConstFetch);
|
||||
}
|
||||
|
||||
return new Arg(BuilderHelpers::normalizeValue($value));
|
||||
}
|
||||
|
||||
/**
|
||||
* @param Arg[] $argumentNodes
|
||||
* @return Arg[]|null
|
||||
*/
|
||||
private function processArrayReplacement(
|
||||
array $argumentNodes,
|
||||
ArgumentDefaultValueReplacer $argumentDefaultValueReplacer
|
||||
): ?array {
|
||||
$argumentValues = $this->resolveArgumentValuesToBeforeRecipe($argumentNodes, $argumentDefaultValueReplacer);
|
||||
if ($argumentValues !== $argumentDefaultValueReplacer->getValueBefore()) {
|
||||
return null;
|
||||
}
|
||||
|
||||
if (is_string($argumentDefaultValueReplacer->getValueAfter())) {
|
||||
$argumentNodes[$argumentDefaultValueReplacer->getPosition()] = $this->normalizeValueToArgument(
|
||||
$argumentDefaultValueReplacer->getValueAfter()
|
||||
);
|
||||
|
||||
// clear following arguments
|
||||
$argumentCountToClear = count($argumentDefaultValueReplacer->getValueBefore());
|
||||
for ($i = $argumentDefaultValueReplacer->getPosition() + 1; $i <= $argumentDefaultValueReplacer->getPosition() + $argumentCountToClear; ++$i) {
|
||||
unset($argumentNodes[$i]);
|
||||
}
|
||||
}
|
||||
|
||||
return $argumentNodes;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param Arg[] $argumentNodes
|
||||
* @return mixed[]
|
||||
*/
|
||||
private function resolveArgumentValuesToBeforeRecipe(
|
||||
array $argumentNodes,
|
||||
ArgumentDefaultValueReplacer $argumentDefaultValueReplacer
|
||||
): array {
|
||||
$argumentValues = [];
|
||||
|
||||
/** @var mixed[] $valueBefore */
|
||||
$valueBefore = $argumentDefaultValueReplacer->getValueBefore();
|
||||
$beforeArgumentCount = count($valueBefore);
|
||||
|
||||
for ($i = 0; $i < $beforeArgumentCount; ++$i) {
|
||||
if (! isset($argumentNodes[$argumentDefaultValueReplacer->getPosition() + $i])) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$nextArg = $argumentNodes[$argumentDefaultValueReplacer->getPosition() + $i];
|
||||
$argumentValues[] = $this->valueResolver->getValue($nextArg->value);
|
||||
}
|
||||
|
||||
return $argumentValues;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,95 @@
|
|||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Rector\Arguments\Rector\FuncCall;
|
||||
|
||||
use PhpParser\Node;
|
||||
use PhpParser\Node\Expr\FuncCall;
|
||||
use Rector\Arguments\ArgumentDefaultValueReplacer;
|
||||
use Rector\Arguments\ValueObject\FuncCallArgumentDefaultValueReplacer;
|
||||
use Rector\Core\Contract\Rector\ConfigurableRectorInterface;
|
||||
use Rector\Core\Rector\AbstractRector;
|
||||
use Symplify\RuleDocGenerator\ValueObject\CodeSample\ConfiguredCodeSample;
|
||||
use Symplify\RuleDocGenerator\ValueObject\RuleDefinition;
|
||||
use Webmozart\Assert\Assert;
|
||||
|
||||
/**
|
||||
* @changelog https://php.watch/versions/8.1/version_compare-operator-restrictions
|
||||
* @changelog https://github.com/rectorphp/rector/issues/6271
|
||||
*
|
||||
* @see \Rector\Tests\Arguments\Rector\FuncCall\FunctionArgumentDefaultValueReplacerRector\FunctionArgumentDefaultValueReplacerRectorTest
|
||||
*/
|
||||
final class FunctionArgumentDefaultValueReplacerRector extends AbstractRector implements ConfigurableRectorInterface
|
||||
{
|
||||
/**
|
||||
* @var string
|
||||
*/
|
||||
public const REPLACED_ARGUMENTS = 'replaced_arguments';
|
||||
|
||||
/**
|
||||
* @var FuncCallArgumentDefaultValueReplacer[]
|
||||
*/
|
||||
private mixed $replacedArguments = [];
|
||||
|
||||
public function __construct(
|
||||
private ArgumentDefaultValueReplacer $argumentDefaultValueReplacer
|
||||
) {
|
||||
}
|
||||
|
||||
public function getRuleDefinition(): RuleDefinition
|
||||
{
|
||||
return new RuleDefinition('Streamline the operator arguments of version_compare function', [
|
||||
new ConfiguredCodeSample(
|
||||
<<<'CODE_SAMPLE'
|
||||
version_compare(PHP_VERSION, '5.6', 'gte');
|
||||
CODE_SAMPLE
|
||||
|
||||
,
|
||||
<<<'CODE_SAMPLE'
|
||||
version_compare(PHP_VERSION, '5.6', 'ge');
|
||||
CODE_SAMPLE
|
||||
,
|
||||
[
|
||||
self::REPLACED_ARGUMENTS => [
|
||||
new FuncCallArgumentDefaultValueReplacer('version_compare', 2, 'gte', 'ge',),
|
||||
],
|
||||
]
|
||||
),
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return array<class-string<Node>>
|
||||
*/
|
||||
public function getNodeTypes(): array
|
||||
{
|
||||
return [FuncCall::class];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param FuncCall $node
|
||||
*/
|
||||
public function refactor(Node $node): ?Node
|
||||
{
|
||||
foreach ($this->replacedArguments as $replacedArgument) {
|
||||
if (! $this->isName($node->name, $replacedArgument->getFunction())) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$this->argumentDefaultValueReplacer->processReplaces($node, $replacedArgument);
|
||||
}
|
||||
|
||||
return $node;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param array<string, FuncCallArgumentDefaultValueReplacer[]> $configuration
|
||||
*/
|
||||
public function configure(array $configuration): void
|
||||
{
|
||||
$replacedArguments = $configuration[self::REPLACED_ARGUMENTS] ?? [];
|
||||
Assert::allIsInstanceOf($replacedArguments, FuncCallArgumentDefaultValueReplacer::class);
|
||||
$this->replacedArguments = $replacedArguments;
|
||||
}
|
||||
}
|
|
@ -5,8 +5,9 @@ declare(strict_types=1);
|
|||
namespace Rector\Arguments\ValueObject;
|
||||
|
||||
use PHPStan\Type\ObjectType;
|
||||
use Rector\Arguments\Contract\ArgumentDefaultValueReplacerInterface;
|
||||
|
||||
final class ArgumentDefaultValueReplacer
|
||||
final class ArgumentDefaultValueReplacer implements ArgumentDefaultValueReplacerInterface
|
||||
{
|
||||
/**
|
||||
* @param mixed $valueBefore
|
||||
|
|
|
@ -0,0 +1,48 @@
|
|||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Rector\Arguments\ValueObject;
|
||||
|
||||
use Rector\Arguments\Contract\ArgumentDefaultValueReplacerInterface;
|
||||
|
||||
final class FuncCallArgumentDefaultValueReplacer implements ArgumentDefaultValueReplacerInterface
|
||||
{
|
||||
/**
|
||||
* @param mixed $valueBefore
|
||||
* @param mixed $valueAfter
|
||||
*/
|
||||
public function __construct(
|
||||
private string $function,
|
||||
private int $position,
|
||||
private $valueBefore,
|
||||
private $valueAfter
|
||||
) {
|
||||
}
|
||||
|
||||
public function getFunction(): string
|
||||
{
|
||||
return $this->function;
|
||||
}
|
||||
|
||||
public function getPosition(): int
|
||||
{
|
||||
return $this->position;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return mixed
|
||||
*/
|
||||
public function getValueBefore()
|
||||
{
|
||||
return $this->valueBefore;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return mixed
|
||||
*/
|
||||
public function getValueAfter()
|
||||
{
|
||||
return $this->valueAfter;
|
||||
}
|
||||
}
|
|
@ -69,9 +69,9 @@ CODE_SAMPLE
|
|||
$arrayVariable = $node->args[1]->value;
|
||||
|
||||
/** @var Assign|Node|null $previousAssignArraysKeysFuncCall */
|
||||
$previousAssignArraysKeysFuncCall = $this->betterNodeFinder->findFirstPreviousOfNode($node, function (Node $node) use (
|
||||
$arrayVariable
|
||||
): bool {
|
||||
$previousAssignArraysKeysFuncCall = $this->betterNodeFinder->findFirstPreviousOfNode($node, function (
|
||||
Node $node
|
||||
) use ($arrayVariable): bool {
|
||||
// breaking out of scope
|
||||
if ($node instanceof FunctionLike) {
|
||||
return true;
|
||||
|
|
Loading…
Reference in New Issue
Block a user