Skip to content
This repository has been archived by the owner on Jan 29, 2020. It is now read-only.

Updated ValueInjection to check array values as these can be exportable #50

Merged
merged 3 commits into from
Jan 10, 2019
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,8 @@ All notable changes to this project will be documented in this file, in reverse

### Fixed

- Nothing.
- [#50](https://github.com/zendframework/zend-di/pull/50) fixes recognizing array values
as exportable, so factories can be generated for default array values.

## 3.1.0 - 2018-10-23

Expand Down
39 changes: 33 additions & 6 deletions src/Resolver/ValueInjection.php
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,16 @@
namespace Zend\Di\Resolver;

use Psr\Container\ContainerInterface;
use ReflectionObject;
use ReflectionMethod;
use Zend\Di\Exception\LogicException;

use function is_array;
use function is_object;
use function is_scalar;
use function method_exists;
use function trigger_error;
use function var_export;

use const E_USER_DEPRECATED;

/**
Expand Down Expand Up @@ -68,15 +74,36 @@ public function export() : string
*/
public function isExportable() : bool
{
if (is_scalar($this->value) || ($this->value === null)) {
return $this->isExportableRecursive($this->value);
}

/**
* Check if the provided value is exportable.
* For arrays it uses recursion.
*
* @param mixed $value
* @return bool
michalbundyra marked this conversation as resolved.
Show resolved Hide resolved
*/
private function isExportableRecursive($value) : bool
{
if (is_scalar($value) || $value === null) {
return true;
}

if (is_array($value)) {
foreach ($value as $item) {
if (! $this->isExportableRecursive($item)) {
return false;
}
}

return true;
}

if (is_object($this->value) && method_exists($this->value, '__set_state')) {
$reflection = new ReflectionObject($this->value);
$method = $reflection->getMethod('__set_state');
if (is_object($value) && method_exists($value, '__set_state')) {
$method = new ReflectionMethod($value, '__set_state');

return ($method->isStatic() && $method->isPublic());
return $method->isStatic() && $method->isPublic();
}

return false;
Expand Down
19 changes: 19 additions & 0 deletions test/Resolver/ValueInjectionTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,23 @@ public function provideExportableValues()
'null' => [null],
'float' => [microtime(true)],
'object' => [new TestAsset\Resolver\ExportableValue()],
'array' => [[]],
'array-string' => [['TestValue', 'OtherValue']],
'array-int' => [[123, 456]],
'array-mixed' => [
[
new TestAsset\Resolver\ExportableValue(),
[1],
null,
false,
true,
time(),
microtime(true),
[[], []],
uniqid(),
[],
],
],
];
}

Expand All @@ -111,6 +128,8 @@ public function provideUnexportableItems()
'stream' => [$this->streamFixture],
'noSetState' => [new TestAsset\Resolver\UnexportableValue1()],
'privateSetState' => [new TestAsset\Resolver\UnexportableValue2()],
'arrayNoSetState' => [[new TestAsset\Resolver\UnexportableValue1()]],
'arrayPrivateSetState' => [[new TestAsset\Resolver\UnexportableValue2()]],
];
}

Expand Down