Skip to content
Snippets Groups Projects
Verified Commit e792477b authored by William Desportes's avatar William Desportes :sailboat:
Browse files

New upstream version 3.2.0

parent 5585e4a8
No related branches found
Tags upstream/3.2.0
No related merge requests found
Showing
with 632 additions and 42 deletions
......@@ -2,6 +2,14 @@
All notable changes to this project will be documented in this file.
This project adheres to [Semantic Versioning](http://semver.org/).
## [3.1.0] - 2023-07-18
### Added
- Support of UnitEnum and BackedEnum deserialization (PHP > 8.1). Thanks @marcimat
- Support to multiple closure serializers
- Built in closure serializer using opis/closure
### Fixed
- Fixed deprecated with DateTimeImmutable deserialization with PHP 8.2
## [3.0.0] - 2020-07-20
### Fixed
- Fixed DateTime & DateTimeImmutable serialization in PHP 7.4+. Thanks @przemyslaw-bogusz
......
......@@ -41,7 +41,7 @@ Limitations:
This project should not be confused with `JsonSerializable` interface added on PHP 5.4. This interface is used on
`json_encode` to encode the objects. There is no unserialization with this interface, differently from this project.
*Json Serializer requires PHP >= 7.0 and tested until PHP 7.4*
*Json Serializer requires PHP >= 7.0 and tested until PHP 8.2*
## Example
......@@ -98,17 +98,16 @@ $json = $serializer->serialize($data);
```
## Serializing Closures
## Serializing Closure
For serializing PHP closures you have to pass an object implementing `SuperClosure\SerializerInterface`.
This interface is provided by the project [SuperClosure](https://github.com/jeremeamia/super_closure). This
project also provides a closure serializer that implements this interface.
For serializing PHP closures you can either use [OpisClosure](https://github.com/opis/closure) (preferred) or
[SuperClosure](https://github.com/jeremeamia/super_closure) (the project is abandoned, so kept here for backward
compatibility).
Closure serialization has some limitations. Please check the SuperClosure project to check if it fits your
needs.
Closure serialization has some limitations. Please check the OpisClosure or SuperClosure project to check if it fits
your needs.
To use the SuperClosure with JsonSerializer, just pass the SuperClosure object as the first parameter
on JsonSerializer constructor. Example:
To use the OpisClosure with JsonSerializer, just add it to the closure serializer list. Example:
```php
$toBeSerialized = [
......@@ -122,13 +121,15 @@ $toBeSerialized = [
}
];
$superClosure = new SuperClosure\Serializer();
$jsonSerializer = new Zumba\JsonSerializer\JsonSerializer($superClosure);
$jsonSerializer = new \Zumba\JsonSerializer\JsonSerializer();
$jsonSerializer->addClosureSerializer(new \Zumba\JsonSerializer\ClosureSerializer\OpisClosureSerializer());
$serialized = $jsonSerializer->serialize($toBeSerialized);
```
PS: JsonSerializer does not have a hard dependency of SuperClosure. If you want to use both projects
make sure you add both on your composer requirements.
You can load multiple closure serializers in case you are migrating from SuperClosure to OpisClosure for example.
PS: JsonSerializer does not have a hard dependency of OpisClosure or SuperClosure. If you want to use both projects
make sure you add both on your composer requirements and load them with `addClosureSerializer()` method.
## Custom Serializers
......
......@@ -3,7 +3,7 @@
"type": "library",
"description": "Serialize PHP variables, including objects, in JSON format. Support to unserialize it too.",
"keywords": ["json", "serialize", "serializer"],
"homepage": "http://tech.zumba.com",
"homepage": "https://tech.zumba.com",
"license": "MIT",
"scripts": {
"test": "phpunit --colors=always"
......@@ -23,21 +23,15 @@
"ext-mbstring": "*"
},
"suggest": {
"jeremeamia/superclosure": "Allow to serialize PHP closures"
"opis/closure": "Allow to serialize PHP closures"
},
"require-dev": {
"phpunit/phpunit": ">=6.0 <10.0"
"phpunit/phpunit": ">=6.0 <11.0"
},
"autoload": {
"psr-4": {
"Zumba\\": "src/",
"Zumba\\JsonSerializer\\Test\\": "tests/"
}
},
"archive": {
"exclude": [
"/tests",
"/phpunit.xml"
]
}
}
<?php
namespace Zumba\JsonSerializer\ClosureSerializer;
use Closure;
interface ClosureSerializer {
/**
* Serialize a closure
*
* @param Closure $closure
* @return string
*/
public function serialize(Closure $closure);
/**
* Unserialize a closure
*
* @param string $serialized
* @return Closure
*/
public function unserialize($serialized);
}
<?php
namespace Zumba\JsonSerializer\ClosureSerializer;
class ClosureSerializerManager {
/**
* Closure serializer instances
*
* @var array
*/
protected $closureSerializer = array();
/**
* Prefered closure serializer
*/
protected $preferred = array(
OpisClosureSerializer::class,
SuperClosureSerializer::class
);
/**
* Set closure engine
*
* @param ClosureSerializer $closureSerializer
* @return self
*/
public function addSerializer(ClosureSerializer $closureSerializer)
{
$classname = $closureSerializer::class;
$this->closureSerializer[$classname] = $closureSerializer;
return $this;
}
/**
* Get preferred closure serializer
*
* @return ClosureSerializer|null
*/
public function getPreferredSerializer()
{
if (empty($this->closureSerializer)) {
return null;
}
foreach ($this->preferred as $preferred) {
if (isset($this->closureSerializer[$preferred])) {
return $this->closureSerializer[$preferred];
}
}
return current($this->closureSerializer);
}
/**
* Get closure serializer
*
* @param string $classname
* @return ClosureSerializer|null
*/
public function getSerializer(string $classname)
{
if (isset($this->closureSerializer[$classname])) {
return $this->closureSerializer[$classname];
}
return null;
}
}
<?php
namespace Zumba\JsonSerializer\ClosureSerializer;
use Closure;
use Opis\Closure\SerializableClosure as OpisSerializableClosure;
class OpisClosureSerializer implements ClosureSerializer {
/**
* Serialize a closure
*
* @param Closure $closure
* @return string
*/
public function serialize(Closure $closure)
{
return serialize(new OpisSerializableClosure($closure));
}
/**
* Unserialize a closure
*
* @param string $serialized
* @return Closure
*/
public function unserialize($serialized)
{
return unserialize($serialized)->getClosure();
}
}
<?php
namespace Zumba\JsonSerializer\ClosureSerializer;
use Closure;
use SuperClosure\SerializerInterface as SuperClosureSerializerInterface;
class SuperClosureSerializer implements ClosureSerializer {
/**
* Closure serializer instance
*
* @var SuperClosureSerializerInterface
*/
protected $serializer;
/**
* Closure serializer instance
*
* @var SuperClosureSerializerInterface
*/
public function __construct(SuperClosureSerializerInterface $serializer)
{
$this->serializer = $serializer;
}
/**
* Serialize a closure
*
* @param Closure $closure
* @return string
*/
public function serialize(Closure $closure)
{
return $this->serializer->serialize($closure);
}
/**
* Unserialize a closure
*
* @param string $serialized
* @return Closure
*/
public function unserialize($serialized)
{
return $this->serializer->unserialize($serialized);
}
}
......@@ -49,11 +49,11 @@ class JsonSerializer
protected $objectMappingIndex = 0;
/**
* Closure serializer instance
* Closure manager
*
* @var ClosureSerializerInterface
* @var ClosureSerializer\ClosureSerializerManager
*/
protected $closureSerializer;
protected $closureManager;
/**
* Map of custom object serializers
......@@ -72,17 +72,33 @@ class JsonSerializer
/**
* Constructor.
*
* @param ClosureSerializerInterface $closureSerializer
* @param ClosureSerializerInterface $closureSerializer This parameter is deprecated and will be removed in 5.0.0. Use addClosureSerializer() instead.
* @param array $customObjectSerializerMap
*/
public function __construct(
ClosureSerializerInterface $closureSerializer = null,
$customObjectSerializerMap = []
) {
$this->closureSerializer = $closureSerializer;
$this->closureManager = new ClosureSerializer\ClosureSerializerManager();
if ($closureSerializer) {
trigger_error(
'Passing a ClosureSerializerInterface to the constructor is deprecated and will be removed in 4.0.0. Use addClosureSerializer() instead.',
E_USER_DEPRECATED
);
$this->addClosureSerializer(new ClosureSerializer\SuperClosureSerializer($closureSerializer));
}
$this->customObjectSerializerMap = (array)$customObjectSerializerMap;
}
/**
* Add a closure serializer
*/
public function addClosureSerializer(ClosureSerializer\ClosureSerializer $closureSerializer)
{
$this->closureManager->addSerializer($closureSerializer);
}
/**
* Serialize the value in JSON
*
......@@ -242,12 +258,14 @@ class JsonSerializer
return array_map([$this, __FUNCTION__], $value);
}
if ($value instanceof \Closure) {
if (!$this->closureSerializer) {
$closureSerializer = $this->closureManager->getPreferredSerializer();
if (!$closureSerializer) {
throw new JsonSerializerException('Closure serializer not given. Unable to serialize closure.');
}
return [
static::CLOSURE_IDENTIFIER_KEY => true,
'value' => $this->closureSerializer->serialize($value)
'serializer' => $closureSerializer::class,
'value' => $closureSerializer->serialize($value)
];
}
return $this->serializeObject($value);
......@@ -349,10 +367,12 @@ class JsonSerializer
}
if (!empty($value[static::CLOSURE_IDENTIFIER_KEY])) {
if (!$this->closureSerializer) {
$serializerClass = isset($value['serializer']) ? $value['serializer'] : ClosureSerializer\SuperClosureSerializer::class;
$serializer = $this->closureManager->getSerializer($serializerClass);
if (!$serializer) {
throw new JsonSerializerException('Closure serializer not provided to unserialize closure');
}
return $this->closureSerializer->unserialize($value['value']);
return $serializer->unserialize($value['value']);
}
return array_map([$this, __FUNCTION__], $value);
......@@ -428,12 +448,18 @@ class JsonSerializer
throw new JsonSerializerException('Unable to find class ' . $className);
}
if ($className === 'DateTime') {
if ($className === 'DateTime' || $className === 'DateTimeImmutable') {
$obj = $this->restoreUsingUnserialize($className, $value);
$this->objectMapping[$this->objectMappingIndex++] = $obj;
return $obj;
}
if (is_subclass_of($className, \UnitEnum::class)) {
$obj = constant("$className::{$value['name']}");
$this->objectMapping[$this->objectMappingIndex++] = $obj;
return $obj;
}
if (!$this->isSplList($className)) {
$ref = new ReflectionClass($className);
$obj = $ref->newInstanceWithoutConstructor();
......
<?php
namespace Zumba\JsonSerializer\Test\ClosureSerializer;
use PHPUnit\Framework\TestCase;
use Zumba\JsonSerializer\ClosureSerializer\ClosureSerializerManager;
use Zumba\JsonSerializer\ClosureSerializer\SuperClosureSerializer;
class ClosureSerializerManagerTest extends TestCase
{
public function setUp(): void
{
if (! class_exists(\SuperClosure\SerializerInterface::class)) {
$this->markTestSkipped('Missing jeremeamia/superclosure to run this test');
}
}
public function testAddSerializer() {
$manager = new ClosureSerializerManager();
$this->assertEmpty($manager->getSerializer('foo'));
$manager->addSerializer(new SuperClosureSerializer(new \SuperClosure\Serializer()));
$this->assertNotEmpty($manager->getSerializer(SuperClosureSerializer::class));
}
public function testGetPreferredSerializer() {
$manager = new ClosureSerializerManager();
$this->assertNull($manager->getPreferredSerializer());
$serializer = new SuperClosureSerializer(new \SuperClosure\Serializer());
$manager->addSerializer($serializer);
$this->assertSame($serializer, $manager->getPreferredSerializer());
}
}
<?php
namespace Zumba\JsonSerializer\Test\ClosureSerializer;
use PHPUnit\Framework\TestCase;
use Zumba\JsonSerializer\ClosureSerializer\OpisClosureSerializer;
class OpisClosureSerializerTest extends TestCase
{
public function setUp(): void
{
if (! class_exists(\Opis\Closure\SerializableClosure::class)) {
$this->markTestSkipped('Missing opis/closure to run this test');
}
}
public function testSerialize() {
$closure = function() {
return 'foo';
};
$serializer = new OpisClosureSerializer();
$serialized = $serializer->serialize($closure);
$this->assertNotEmpty($serialized);
$this->assertTrue(is_string($serialized));
$this->assertNotEquals($closure, $serialized);
}
public function testUnserialize() {
$closure = function() {
return 'foo';
};
$serializer = new OpisClosureSerializer();
$serialized = $serializer->serialize($closure);
$unserialized = $serializer->unserialize($serialized);
$this->assertNotEmpty($unserialized);
$this->assertTrue($unserialized instanceof \Closure);
$this->assertEquals($closure(), $unserialized());
}
}
<?php
namespace Zumba\JsonSerializer\Test\ClosureSerializer;
use PHPUnit\Framework\TestCase;
use Zumba\JsonSerializer\ClosureSerializer\SuperClosureSerializer;
class SuperClosureSerializerTest extends TestCase
{
public function setUp(): void
{
if (! class_exists(\SuperClosure\SerializerInterface::class)) {
$this->markTestSkipped('Missing jeremeamia/superclosure to run this test');
}
}
public function testSerialize() {
$closure = function() {
return 'foo';
};
$serializer = new SuperClosureSerializer(new \SuperClosure\Serializer());
$serialized = $serializer->serialize($closure);
$this->assertNotEmpty($serialized);
$this->assertTrue(is_string($serialized));
$this->assertNotEquals($closure, $serialized);
}
public function testUnserialize() {
$closure = function() {
return 'foo';
};
$serializer = new SuperClosureSerializer(new \SuperClosure\Serializer());
$serialized = $serializer->serialize($closure);
$unserialized = $serializer->unserialize($serialized);
$this->assertNotEmpty($unserialized);
$this->assertTrue($unserialized instanceof \Closure);
$this->assertEquals($closure(), $unserialized());
}
}
......@@ -2,10 +2,11 @@
namespace Zumba\JsonSerializer\Test;
use Zumba\JsonSerializer\ClosureSerializer;
use Zumba\JsonSerializer\JsonSerializer;
use Zumba\JsonSerializer\Exception\JsonSerializerException;
use stdClass;
use SuperClosure\Serializer as ClosureSerializer;
use SuperClosure\Serializer as SuperClosureSerializer;
use PHPUnit\Framework\TestCase;
use ReflectionProperty;
......@@ -80,10 +81,8 @@ class JsonSerializerTest extends TestCase
/**
* List of scalar data
*
* @return array
*/
public function scalarData()
public static function scalarData(): array
{
return array(
array('testing', '"testing"'),
......@@ -155,10 +154,8 @@ class JsonSerializerTest extends TestCase
/**
* List of array data
*
* @return array
*/
public function arrayNoObjectData()
public static function arrayNoObjectData(): array
{
return array(
array(array(1, 2, 3), '[1,2,3]'),
......@@ -240,6 +237,146 @@ class JsonSerializerTest extends TestCase
$this->assertInstanceOf('Zumba\JsonSerializer\Test\SupportClasses\EmptyClass', $array['instance']);
}
/**
* Test serialization of Enums
*
* @return void
*/
public function testSerializeEnums()
{
if (PHP_VERSION_ID < 80100) {
$this->markTestSkipped("Enums are only available since PHP 8.1");
}
$unitEnum = SupportEnums\MyUnitEnum::Hearts;
$expected = '{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyUnitEnum","name":"Hearts"}';
$this->assertSame($expected, $this->serializer->serialize($unitEnum));
$backedEnum = SupportEnums\MyBackedEnum::Hearts;
$expected = '{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyBackedEnum","name":"Hearts","value":"H"}';
$this->assertSame($expected, $this->serializer->serialize($backedEnum));
$intBackedEnum = SupportEnums\MyIntBackedEnum::One;
$expected = '{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyIntBackedEnum","name":"One","value":1}';
$this->assertSame($expected, $this->serializer->serialize($intBackedEnum));
}
/**
* Test serialization of multiple Enums
*
* @return void
*/
public function testSerializeMultipleEnums()
{
if (PHP_VERSION_ID < 80100) {
$this->markTestSkipped("Enums are only available since PHP 8.1");
}
$obj = new stdClass();
$obj->enum1 = SupportEnums\MyUnitEnum::Hearts;
$obj->enum2 = SupportEnums\MyBackedEnum::Hearts;
$obj->enum3 = SupportEnums\MyIntBackedEnum::One;
$obj->enum4 = SupportEnums\MyUnitEnum::Hearts;
$obj->enum5 = SupportEnums\MyBackedEnum::Hearts;
$obj->enum6 = SupportEnums\MyIntBackedEnum::One;
$expected = '{"@type":"stdClass","enum1":{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyUnitEnum","name":"Hearts"},"enum2":{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyBackedEnum","name":"Hearts","value":"H"},"enum3":{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyIntBackedEnum","name":"One","value":1},"enum4":{"@type":"@1"},"enum5":{"@type":"@2"},"enum6":{"@type":"@3"}}';
$this->assertSame($expected, $this->serializer->serialize($obj));
}
/**
* Test unserialization of Enums
*
* @return void
*/
public function testUnserializeEnums()
{
if (PHP_VERSION_ID < 80100) {
$this->markTestSkipped("Enums are only available since PHP 8.1");
}
$serialized = '{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyUnitEnum","name":"Hearts"}';
$obj = $this->serializer->unserialize($serialized);
$this->assertInstanceOf('Zumba\JsonSerializer\Test\SupportEnums\MyUnitEnum', $obj);
$this->assertSame(SupportEnums\MyUnitEnum::Hearts, $obj);
$serialized = '{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyBackedEnum","name":"Hearts","value":"H"}';
$obj = $this->serializer->unserialize($serialized);
$this->assertInstanceOf('Zumba\JsonSerializer\Test\SupportEnums\MyBackedEnum', $obj);
$this->assertSame(SupportEnums\MyBackedEnum::Hearts, $obj);
$serialized = '{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyIntBackedEnum","name":"Two","value":2}';
$obj = $this->serializer->unserialize($serialized);
$this->assertInstanceOf('Zumba\JsonSerializer\Test\SupportEnums\MyIntBackedEnum', $obj);
$this->assertSame(SupportEnums\MyIntBackedEnum::Two, $obj);
$this->assertSame(SupportEnums\MyIntBackedEnum::Two->value, $obj->value);
// wrong value of BackedEnum is ignored
$serialized = '{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyBackedEnum","name":"Hearts","value":"S"}';
$obj = $this->serializer->unserialize($serialized);
$this->assertInstanceOf('Zumba\JsonSerializer\Test\SupportEnums\MyBackedEnum', $obj);
$this->assertSame(SupportEnums\MyBackedEnum::Hearts, $obj);
$this->assertSame(SupportEnums\MyBackedEnum::Hearts->value, $obj->value);
}
/**
* Test unserialization of multiple Enums
*
* @return void
*/
public function testUnserializeMultipleEnums()
{
if (PHP_VERSION_ID < 80100) {
$this->markTestSkipped("Enums are only available since PHP 8.1");
}
$obj = new stdClass();
$obj->enum1 = SupportEnums\MyUnitEnum::Hearts;
$obj->enum2 = SupportEnums\MyBackedEnum::Hearts;
$obj->enum3 = SupportEnums\MyIntBackedEnum::One;
$obj->enum4 = SupportEnums\MyUnitEnum::Hearts;
$obj->enum5 = SupportEnums\MyBackedEnum::Hearts;
$obj->enum6 = SupportEnums\MyIntBackedEnum::One;
$serialized = '{"@type":"stdClass","enum1":{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyUnitEnum","name":"Hearts"},"enum2":{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyBackedEnum","name":"Hearts","value":"H"},"enum3":{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyIntBackedEnum","name":"One","value":1},"enum4":{"@type":"@1"},"enum5":{"@type":"@2"},"enum6":{"@type":"@3"}}';
$actualObj = $this->serializer->unserialize($serialized);
$this->assertInstanceOf('stdClass', $actualObj);
$this->assertEquals($obj, $actualObj);
}
/**
* Test unserialization of wrong UnitEnum
*
* @return void
*/
public function testUnserializeWrongUnitEnum() {
if (PHP_VERSION_ID < 80100) {
$this->markTestSkipped("Enums are only available since PHP 8.1");
}
// bad case generate Error
$serialized = '{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyUnitEnum","name":"Circles"}';
$this->expectException(\Error::class);
$this->serializer->unserialize($serialized);
}
/**
* Test unserialization of wrong BackedEnum
*
* @return void
*/
public function testUnserializeWrongBackedEnum() {
if (PHP_VERSION_ID < 80100) {
$this->markTestSkipped("Enums are only available since PHP 8.1");
}
// bad case generate Error
$serialized = '{"@type":"Zumba\\\\JsonSerializer\\\\Test\\\\SupportEnums\\\\MyBackedEnum","name":"Circles","value":"C"}';
$this->expectException(\Error::class);
$this->serializer->unserialize($serialized);
}
/**
* Test serialization of objects using the custom serializers
*
......@@ -296,6 +433,10 @@ class JsonSerializerTest extends TestCase
$date = new \DateTime('2014-06-15 12:00:00', new \DateTimeZone('UTC'));
$obj = $this->serializer->unserialize($this->serializer->serialize($date));
$this->assertSame($date->getTimestamp(), $obj->getTimestamp());
$date = new \DateTimeImmutable('2014-06-15 12:00:00', new \DateTimeZone('UTC'));
$obj = $this->serializer->unserialize($this->serializer->serialize($date));
$this->assertSame($date->getTimestamp(), $obj->getTimestamp());
}
/**
......@@ -303,13 +444,13 @@ class JsonSerializerTest extends TestCase
*
* @return void
*/
public function testSerializationOfClosure()
public function testSerializationOfClosureWithSuperClosureOnConstructor()
{
if (!class_exists('SuperClosure\Serializer')) {
$this->markTestSkipped('SuperClosure is not installed.');
}
$closureSerializer = new ClosureSerializer();
$closureSerializer = new SuperClosureSerializer();
$serializer = new JsonSerializer($closureSerializer);
$serialized = $serializer->serialize(
array(
......@@ -327,6 +468,111 @@ class JsonSerializerTest extends TestCase
$this->assertSame('it works', $unserialized['func']());
}
/**
* Test the serialization of closures providing closure serializer
*
* @return void
*/
public function testSerializationOfClosureWithSuperClosureOnManager()
{
if (!class_exists('SuperClosure\Serializer')) {
$this->markTestSkipped('SuperClosure is not installed.');
}
$closureSerializer = new SuperClosureSerializer();
$serializer = new JsonSerializer();
$serializer->addClosureSerializer(new ClosureSerializer\SuperClosureSerializer($closureSerializer));
$serialized = $serializer->serialize(
array(
'func' => function () {
return 'it works';
},
'nice' => true
)
);
$unserialized = $serializer->unserialize($serialized);
$this->assertTrue(is_array($unserialized));
$this->assertTrue($unserialized['nice']);
$this->assertInstanceOf('Closure', $unserialized['func']);
$this->assertSame('it works', $unserialized['func']());
}
/**
* Test the serialization of closures providing closure serializer
*
* @return void
*/
public function testSerializationOfClosureWitOpisClosure()
{
if (!class_exists('Opis\Closure\SerializableClosure')) {
$this->markTestSkipped('OpisClosure is not installed.');
}
$serializer = new JsonSerializer();
$serializer->addClosureSerializer(new ClosureSerializer\OpisClosureSerializer());
$serialized = $serializer->serialize(
array(
'func' => function () {
return 'it works';
},
'nice' => true
)
);
$unserialized = $serializer->unserialize($serialized);
$this->assertTrue(is_array($unserialized));
$this->assertTrue($unserialized['nice']);
$this->assertInstanceOf('Closure', $unserialized['func']);
$this->assertSame('it works', $unserialized['func']());
}
/**
* Test the serialization of closures providing closure serializer
*
* @return void
*/
public function testSerializationOfClosureWitMultipleClosures()
{
if (!class_exists('SuperClosure\Serializer')) {
$this->markTestSkipped('SuperClosure is not installed.');
}
if (!class_exists('Opis\Closure\SerializableClosure')) {
$this->markTestSkipped('OpisClosure is not installed.');
}
$closureSerializer = new SuperClosureSerializer();
$serializer = new JsonSerializer();
$serializer->addClosureSerializer(new ClosureSerializer\SuperClosureSerializer($closureSerializer));
$serializeData = array(
'func' => function () {
return 'it works';
},
'nice' => true
);
// Make sure it was serialized with SuperClosure
$serialized = $serializer->serialize($serializeData);
echo $serialized;
$this->assertGreaterThanOrEqual(0, strpos($serialized, 'SuperClosure'));
$this->assertFalse(strpos($serialized, 'OpisClosure'));
// Test adding a new preferred closure serializer
$serializer->addClosureSerializer(new ClosureSerializer\OpisClosureSerializer());
$unserialized = $serializer->unserialize($serialized);
$this->assertTrue(is_array($unserialized));
$this->assertTrue($unserialized['nice']);
$this->assertInstanceOf('Closure', $unserialized['func']);
$this->assertSame('it works', $unserialized['func']());
// Serialize again with the new preferred closure serializer
$serialized = $serializer->serialize($serializeData);
$this->assertFalse(strpos($serialized, 'SuperClosure'));
$this->assertGreaterThanOrEqual(0, strpos($serialized, 'OpisClosure'));
}
/**
* Test the unserialization of closures without providing closure serializer
*
......@@ -338,7 +584,7 @@ class JsonSerializerTest extends TestCase
$this->markTestSkipped('SuperClosure is not installed.');
}
$closureSerializer = new ClosureSerializer();
$closureSerializer = new SuperClosureSerializer();
$serializer = new JsonSerializer($closureSerializer);
$serialized = $serializer->serialize(
array(
......
<?php
namespace Zumba\JsonSerializer\Test\SupportEnums;
enum MyBackedEnum: string
{
case Hearts = 'H';
case Diamonds = 'D';
case Clubs = 'C';
case Spades = 'S';
}
<?php
namespace Zumba\JsonSerializer\Test\SupportEnums;
enum MyIntBackedEnum: int
{
case One = 1;
case Two = 2;
}
<?php
namespace Zumba\JsonSerializer\Test\SupportEnums;
enum MyUnitEnum
{
case Hearts;
case Diamonds;
case Clubs;
case Spades;
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment