public function construct(VisitorInterface $visitor, ClassMetadata $metadata, $data, Type $type, DeserializationContext $context)
 {
     if (!$type->is(BlogPost::class)) {
         return parent::construct($visitor, $metadata, $data, $type, $context);
     }
     return new BlogPost('This is a nice title.', new Author('Foo Bar'), new \DateTime('2011-07-30 00:00', new \DateTimeZone('UTC')), new Publisher('Bar Foo'));
 }
Example #2
0
 protected function getElementType(Type $type)
 {
     if (0 === $type->countParams()) {
         return null;
     }
     $params = $type->getParams();
     if (isset($params[1]) && $params[1] instanceof Type) {
         return $params[1];
     }
     return $params[0];
 }
Example #3
0
 public function testFromArray()
 {
     $data = ['cost' => ['price' => 2.5]];
     $expected = new Order(new Price(2.5));
     $result = $this->serializer->fromArray($data, Type::from(Order::class));
     $this->assertEquals($expected, $result);
 }
 public function testDoesNotRewriteCustomType()
 {
     $event = $this->createEvent($obj = new SimpleObjectProxy('a', 'b'), Type::from('FakedName'));
     $this->subscriber->onPreSerialize($event);
     $this->assertEquals(Type::from('FakedName'), $event->getType());
     $this->assertTrue($obj->__isInitialized());
 }
Example #5
0
 public function testBlogPostCaseInsensitive()
 {
     $m = new ClassMetadata(new \ReflectionClass('Kcs\\Serializer\\Tests\\Fixtures\\BlogPost'));
     $this->getLoaderForSubDir('case')->loadClassMetadata($m);
     $p = new PropertyMetadata($m->getName(), 'title');
     $p->type = Type::from('string');
     $this->assertEquals($p, $m->getAttributeMetadata('title'));
 }
 public function visitArray($data, Type $type, Context $context)
 {
     if (!is_array($data)) {
         throw new RuntimeException(sprintf('Expected array, but got %s: %s', gettype($data), json_encode($data)));
     }
     // If no further parameters were given, keys/values are just passed as is.
     if (!$type->hasParam(0)) {
         $this->setData($data);
         return $data;
     }
     switch ($type->countParams()) {
         case 1:
             // Array is a list.
             $listType = $type->getParam(0);
             $result = [];
             foreach ($data as $v) {
                 $result[] = $context->accept($v, $listType);
             }
             $this->setData($result);
             return $result;
         case 2:
             // Array is a map.
             $keyType = $type->getParam(0);
             $entryType = $type->getParam(1);
             $result = [];
             foreach ($data as $k => $v) {
                 $result[$context->accept($k, $keyType)] = $context->accept($v, $entryType);
             }
             $this->setData($result);
             return $result;
         default:
             throw new RuntimeException(sprintf('Array type cannot have more than 2 parameters, but got %s.', json_encode($type->getParams())));
     }
 }
Example #7
0
 public function testAccessorAttributes()
 {
     $m = new ClassMetadata(new \ReflectionClass('Kcs\\Serializer\\Tests\\Fixtures\\GetSetObject'));
     $this->getLoader()->loadClassMetadata($m);
     $p = new PropertyMetadata($m->getName(), 'name');
     $p->type = Type::from('string');
     $p->getter = 'getTrimmedName';
     $p->setter = 'setCapitalizedName';
     $this->assertEquals($p, $m->getAttributeMetadata('name'));
 }
    public function testBuildWithoutAnythingElse()
    {
        $serializer = $this->builder->build();
        $this->assertEquals('"foo"', $serializer->serialize('foo', 'json'));
        $this->assertEquals('<?xml version="1.0" encoding="UTF-8"?>
<result><![CDATA[foo]]></result>
', $serializer->serialize('foo', 'xml'));
        $this->assertEquals('foo
', $serializer->serialize('foo', 'yml'));
        $this->assertEquals('foo', $serializer->deserialize('"foo"', Type::from('string'), 'json'));
        $this->assertEquals('foo', $serializer->deserialize('<?xml version="1.0" encoding="UTF-8"?><result><![CDATA[foo]]></result>', Type::from('string'), 'xml'));
    }
Example #9
0
    }
    return $post;
}
$serializer = \Kcs\Serializer\SerializerBuilder::create()->setEventDispatcher(new \Symfony\Component\EventDispatcher\EventDispatcher())->build();
$collection = createCollection();
$metrics = [];
$f = function ($format) use($serializer, $collection) {
    $serializer->serialize($collection, $format);
};
// Load all necessary classes into memory.
$f('array');
$table = new \Symfony\Component\Console\Helper\Table($output);
$table->setHeaders(['Format', 'Direction', 'Time']);
$progressBar = new \Symfony\Component\Console\Helper\ProgressBar($output, 8);
$progressBar->start();
foreach (['array', 'json', 'yml', 'xml'] as $format) {
    $table->addRow([$format, 'serialize', benchmark($f, $format)]);
    $progressBar->advance();
}
$serialized = ['array' => $serializer->serialize($collection, 'array'), 'json' => $serializer->serialize($collection, 'json'), 'yml' => $serializer->serialize($collection, 'yml'), 'xml' => $serializer->serialize($collection, 'xml')];
$type = new \Kcs\Serializer\Type\Type('array', [\Kcs\Serializer\Type\Type::from(\Kcs\Serializer\Tests\Fixtures\BlogPost::class)]);
$d = function ($format) use($serializer, $serialized, $type) {
    $serializer->deserialize($serialized[$format], $type, $format);
};
foreach (['array', 'json', 'yml', 'xml'] as $format) {
    $table->addRow([$format, 'deserialize', benchmark($d, $format)]);
    $progressBar->advance();
}
$progressBar->finish();
$progressBar->clear();
$table->render();
Example #10
0
 private function visitArray(VisitorInterface $visitor, $data, Type $type, $context)
 {
     if ($context instanceof SerializationContext && $type->hasParam(0) && !$type->hasParam(1)) {
         $data = array_values($data);
     }
     return $visitor->visitArray($data, $type, $context);
 }
Example #11
0
 public function setType($type)
 {
     $this->type = Type::parse($type);
 }
 public function visitDouble($data, Type $type, Context $context)
 {
     if ($this->isNullNode($data)) {
         return $this->visitNull(null, Type::null(), $context);
     }
     return parent::visitDouble($data, $type, $context);
 }
Example #13
0
 public function testXmlNamespaceInheritanceMetadata()
 {
     $m = new ClassMetadata(new \ReflectionClass(SimpleClassObject::class));
     $this->getLoader()->loadClassMetadata($m);
     $this->assertNotNull($m);
     $this->assertCount(3, $m->xmlNamespaces);
     $this->assertArrayHasKey('old_foo', $m->xmlNamespaces);
     $this->assertEquals('http://old.foo.example.org', $m->xmlNamespaces['old_foo']);
     $this->assertArrayHasKey('foo', $m->xmlNamespaces);
     $this->assertEquals('http://foo.example.org', $m->xmlNamespaces['foo']);
     $this->assertArrayHasKey('new_foo', $m->xmlNamespaces);
     $this->assertEquals('http://new.foo.example.org', $m->xmlNamespaces['new_foo']);
     $this->assertCount(3, $m->getAttributesMetadata());
     $p = new PropertyMetadata($m->getName(), 'foo');
     $p->type = Type::from('string');
     $p->xmlNamespace = 'http://old.foo.example.org';
     $p->xmlAttribute = true;
     $p->accessorType = PropertyMetadata::ACCESS_TYPE_PROPERTY;
     $this->assertEquals($p, $m->getAttributeMetadata('foo'));
     $p = new PropertyMetadata($m->getName(), 'bar');
     $p->type = Type::from('string');
     $p->xmlNamespace = 'http://foo.example.org';
     $p->accessorType = PropertyMetadata::ACCESS_TYPE_PROPERTY;
     $this->assertEquals($p, $m->getAttributeMetadata('bar'));
     $p = new PropertyMetadata($m->getName(), 'moo');
     $p->type = Type::from('string');
     $p->xmlNamespace = 'http://new.foo.example.org';
     $p->accessorType = PropertyMetadata::ACCESS_TYPE_PROPERTY;
     $this->assertEquals($p, $m->getAttributeMetadata('moo'));
     $subm = new ClassMetadata(new \ReflectionClass(SimpleSubClassObject::class));
     $this->getLoader()->loadClassMetadata($subm);
     $this->assertNotNull($subm);
     $this->assertCount(2, $subm->xmlNamespaces);
     $this->assertArrayHasKey('old_foo', $subm->xmlNamespaces);
     $this->assertEquals('http://foo.example.org', $subm->xmlNamespaces['old_foo']);
     $this->assertArrayHasKey('foo', $subm->xmlNamespaces);
     $this->assertEquals('http://better.foo.example.org', $subm->xmlNamespaces['foo']);
     $this->assertCount(3, $subm->getAttributesMetadata());
     $p = new PropertyMetadata($subm->getName(), 'moo');
     $p->type = Type::from('string');
     $p->xmlNamespace = 'http://better.foo.example.org';
     $p->accessorType = PropertyMetadata::ACCESS_TYPE_PROPERTY;
     $this->assertEquals($p, $subm->getAttributeMetadata('moo'));
     $p = new PropertyMetadata($subm->getName(), 'baz');
     $p->type = Type::from('string');
     $p->xmlNamespace = 'http://foo.example.org';
     $p->accessorType = PropertyMetadata::ACCESS_TYPE_PROPERTY;
     $this->assertEquals($p, $subm->getAttributeMetadata('baz'));
     $p = new PropertyMetadata($subm->getName(), 'qux');
     $p->type = Type::from('string');
     $p->xmlNamespace = 'http://new.foo.example.org';
     $p->accessorType = PropertyMetadata::ACCESS_TYPE_PROPERTY;
     $this->assertEquals($p, $subm->getAttributeMetadata('qux'));
     $subm->merge($m);
     $this->assertNotNull($subm);
     $this->assertCount(3, $subm->xmlNamespaces);
     $this->assertArrayHasKey('old_foo', $subm->xmlNamespaces);
     $this->assertEquals('http://foo.example.org', $subm->xmlNamespaces['old_foo']);
     $this->assertArrayHasKey('foo', $subm->xmlNamespaces);
     $this->assertEquals('http://better.foo.example.org', $subm->xmlNamespaces['foo']);
     $this->assertArrayHasKey('new_foo', $subm->xmlNamespaces);
     $this->assertEquals('http://new.foo.example.org', $subm->xmlNamespaces['new_foo']);
     $this->assertCount(5, $subm->getAttributesMetadata());
     $p = new PropertyMetadata($subm->getName(), 'moo');
     $p->type = Type::from('string');
     $p->xmlNamespace = 'http://better.foo.example.org';
     $p->accessorType = PropertyMetadata::ACCESS_TYPE_PROPERTY;
     $this->assertEquals($p, $subm->getAttributeMetadata('moo'));
     $p = new PropertyMetadata($subm->getName(), 'baz');
     $p->type = Type::from('string');
     $p->xmlNamespace = 'http://foo.example.org';
     $p->accessorType = PropertyMetadata::ACCESS_TYPE_PROPERTY;
     $this->assertEquals($p, $subm->getAttributeMetadata('baz'));
     $p = new PropertyMetadata($subm->getName(), 'qux');
     $p->type = Type::from('string');
     $p->xmlNamespace = 'http://new.foo.example.org';
     $p->accessorType = PropertyMetadata::ACCESS_TYPE_PROPERTY;
     $this->assertEquals($p, $subm->getAttributeMetadata('qux'));
     if (defined('HHVM_VERSION')) {
         $this->markTestSkipped('This test executes partially in HHVM due to wrong class reported in PropertyMetadata');
         return;
     }
     $p = new PropertyMetadata($subm->getName(), 'foo');
     $p->type = Type::from('string');
     $p->xmlNamespace = 'http://old.foo.example.org';
     $p->xmlAttribute = true;
     $p->class = 'Kcs\\Serializer\\Tests\\Fixtures\\SimpleClassObject';
     $p->accessorType = PropertyMetadata::ACCESS_TYPE_PROPERTY;
     $this->assertEquals($p, $subm->getAttributeMetadata('foo'));
     $p = new PropertyMetadata($subm->getName(), 'bar');
     $p->type = Type::from('string');
     $p->xmlNamespace = 'http://foo.example.org';
     $p->class = 'Kcs\\Serializer\\Tests\\Fixtures\\SimpleClassObject';
     $p->accessorType = PropertyMetadata::ACCESS_TYPE_PROPERTY;
     $this->assertEquals($p, $subm->getAttributeMetadata('bar'));
 }
Example #14
0
 /**
  * @return string
  * @param Type $type
  */
 private function getFormat(Type $type)
 {
     return $type->hasParam(0) ? $type->getParam(0) : $this->defaultFormat;
 }
Example #15
0
 public function getTypes()
 {
     $types = [['string', Type::from('string')], ['array<Foo>', new Type('array', [Type::from('Foo')])], ['array<Foo,Bar>', new Type('array', [Type::from('Foo'), Type::from('Bar')])], ['array<Foo\\Bar, Baz\\Boo>', new Type('array', [Type::from('Foo\\Bar'), Type::from('Baz\\Boo')])], ['a<b<c,d>,e>', new Type('a', [new Type('b', [Type::from('c'), Type::from('d')]), Type::from('e')])], ['Foo', Type::from('Foo')], ['Foo\\Bar', Type::from('Foo\\Bar')], ['Foo<"asdf asdf">', new Type('Foo', ['asdf asdf'])]];
     return $types;
 }
 /**
  * @dataProvider getPrimitiveTypes
  */
 public function testPrimitiveTypes($primitiveType, $data)
 {
     $visitor = $this->serializationVisitors['json'];
     $functionToCall = 'visit' . ucfirst($primitiveType);
     $result = $visitor->{$functionToCall}($data, Type::null(), $this->createMock(Context::class));
     if ($primitiveType == 'double') {
         $primitiveType = 'float';
     }
     $this->assertInternalType($primitiveType, $result);
 }
 protected function setUp()
 {
     $loader = new AnnotationLoader();
     $loader->setReader(new AnnotationReader());
     $this->factory = new MetadataFactory($loader);
     $this->handlerRegistry = new HandlerRegistry();
     $this->handlerRegistry->registerSubscribingHandler(new ConstraintViolationHandler());
     $this->handlerRegistry->registerSubscribingHandler(new DateHandler());
     $this->handlerRegistry->registerSubscribingHandler(new FormErrorHandler(new IdentityTranslator(new MessageSelector())));
     $this->handlerRegistry->registerSubscribingHandler(new PhpCollectionHandler());
     $this->handlerRegistry->registerSubscribingHandler(new ArrayCollectionHandler());
     $this->handlerRegistry->registerHandler(Direction::DIRECTION_SERIALIZATION, 'AuthorList', function (VisitorInterface $visitor, $object, Type $type, Context $context) {
         return $visitor->visitArray(iterator_to_array($object), $type, $context);
     });
     $this->handlerRegistry->registerHandler(Direction::DIRECTION_DESERIALIZATION, 'AuthorList', function (VisitorInterface $visitor, $data, $type, Context $context) {
         $type = new Type('array', [Type::from('integer'), Type::from(Author::class)]);
         $elements = $context->accept($data, $type);
         $list = new AuthorList();
         foreach ($elements as $author) {
             $list->add($author);
         }
         return $list;
     });
     $this->dispatcher = new EventDispatcher();
     $this->dispatcher->addSubscriber(new DoctrineProxySubscriber());
     $namingStrategy = new SerializedNameAnnotationStrategy(new CamelCaseNamingStrategy());
     $objectConstructor = new UnserializeObjectConstructor();
     $this->serializationVisitors = ['array' => new GenericSerializationVisitor($namingStrategy), 'json' => new JsonSerializationVisitor($namingStrategy), 'xml' => new XmlSerializationVisitor($namingStrategy), 'yml' => new YamlSerializationVisitor($namingStrategy)];
     $this->deserializationVisitors = ['array' => new GenericDeserializationVisitor($namingStrategy), 'xml' => new XmlDeserializationVisitor($namingStrategy), 'yml' => new YamlDeserializationVisitor($namingStrategy), 'json' => new JsonDeserializationVisitor($namingStrategy)];
     $this->serializer = new Serializer($this->factory, $this->handlerRegistry, $objectConstructor, $this->serializationVisitors, $this->deserializationVisitors, $this->dispatcher);
 }
 public function testWhitelistedDocumentTypesAreAllowed()
 {
     $this->deserializationVisitors['xml']->setDoctypeWhitelist(['<!DOCTYPE authorized SYSTEM "http://authorized_url.dtd">', '<!DOCTYPE author [<!ENTITY foo SYSTEM "php://filter/read=convert.base64-encode/resource=' . basename(__FILE__) . '">]>']);
     $this->serializer->deserialize('<?xml version="1.0"?>
         <!DOCTYPE authorized SYSTEM "http://authorized_url.dtd">
         <foo></foo>', Type::from('stdClass'), 'xml');
     $this->serializer->deserialize('<?xml version="1.0"?>
         <!DOCTYPE author [
             <!ENTITY foo SYSTEM "php://filter/read=convert.base64-encode/resource=' . basename(__FILE__) . '">
         ]>
         <foo></foo>', Type::from('stdClass'), 'xml');
 }