From 08d2a007cc64baaf282b24e79d3930ec670cd213 Mon Sep 17 00:00:00 2001 From: webchick <webchick@24967.no-reply.drupal.org> Date: Wed, 23 Jan 2013 09:47:54 -0800 Subject: [PATCH] Issue #1854874 by alexpott, damiankloip, linclark: Add serializer support for XML. --- core/lib/Drupal/Core/CoreBundle.php | 1 + .../Drupal/Core/Serialization/XmlEncoder.php | 72 +++++++++++++++++++ .../Serialization/EntitySerializationTest.php | 33 ++++++++- 3 files changed, 104 insertions(+), 2 deletions(-) create mode 100644 core/lib/Drupal/Core/Serialization/XmlEncoder.php diff --git a/core/lib/Drupal/Core/CoreBundle.php b/core/lib/Drupal/Core/CoreBundle.php index e70b1fc62c6b..bc6afef4267a 100644 --- a/core/lib/Drupal/Core/CoreBundle.php +++ b/core/lib/Drupal/Core/CoreBundle.php @@ -254,6 +254,7 @@ public function build(ContainerBuilder $container) { $container->register('serializer.normalizer.list', 'Drupal\Core\Serialization\ListNormalizer')->addTag('normalizer'); $container->register('serializer.normalizer.typed_data', 'Drupal\Core\Serialization\TypedDataNormalizer')->addTag('normalizer'); $container->register('serializer.encoder.json', 'Drupal\Core\Serialization\JsonEncoder')->addTag('encoder'); + $container->register('serializer.encoder.xml', 'Drupal\Core\Serialization\XmlEncoder')->addTag('encoder'); $container->register('flood', 'Drupal\Core\Flood\DatabaseBackend') ->addArgument(new Reference('database')); diff --git a/core/lib/Drupal/Core/Serialization/XmlEncoder.php b/core/lib/Drupal/Core/Serialization/XmlEncoder.php new file mode 100644 index 000000000000..7235af3aa7a6 --- /dev/null +++ b/core/lib/Drupal/Core/Serialization/XmlEncoder.php @@ -0,0 +1,72 @@ +<?php + +/** + * @file + * Contains \Drupal\Core\Serialization\XmlEncoder. + */ + +namespace Drupal\Core\Serialization; + +use Symfony\Component\Serializer\Encoder\EncoderInterface; +use Symfony\Component\Serializer\Encoder\DecoderInterface; +use Symfony\Component\Serializer\Encoder\SerializerAwareEncoder; +use Symfony\Component\Serializer\Encoder\XmlEncoder as BaseXmlEncoder; + +/** + * Adds XML support for serializer. + * + * This acts as a wrapper class for Symfony's XmlEncoder so that it is not + * implementing NormalizationAwareInterface, and can be normalized externally. + */ +class XmlEncoder extends SerializerAwareEncoder implements EncoderInterface, DecoderInterface { + + /** + * The formats that this Encoder supports. + * + * @var array + */ + static protected $format = array('xml'); + + /** + * An instance of the Symfony XmlEncoder to perform the actual encoding. + * + * @var \Symfony\Component\Serializer\Encoder\XmlEncoder + */ + protected $baseEncoder; + + /** + * Constucts the XmlEncoder object, creating a BaseXmlEncoder class also. + */ + public function __construct() { + $this->baseEncoder = new BaseXmlEncoder(); + } + + /** + * Implements \Symfony\Component\Serializer\Encoder\EncoderInterface::encode(). + */ + public function encode($data, $format){ + $normalized = $this->serializer->normalize($data, $format); + return $this->baseEncoder->encode($normalized, $format); + } + + /** + * Implements \Symfony\Component\Serializer\Encoder\JsonEncoder::supportsEncoding(). + */ + public function supportsEncoding($format) { + return in_array($format, static::$format); + } + + /** + * Implements \Symfony\Component\Serializer\Encoder\EncoderInterface::decode(). + */ + public function decode($data, $format){ + return $this->baseEncoder->decode($data, $format); + } + + /** + * Implements \Symfony\Component\Serializer\Encoder\JsonEncoder::supportsDecoding(). + */ + public function supportsDecoding($format) { + return in_array($format, static::$format); + } +} diff --git a/core/modules/system/lib/Drupal/system/Tests/Serialization/EntitySerializationTest.php b/core/modules/system/lib/Drupal/system/Tests/Serialization/EntitySerializationTest.php index ea3c96039891..89fa5ce0b856 100644 --- a/core/modules/system/lib/Drupal/system/Tests/Serialization/EntitySerializationTest.php +++ b/core/modules/system/lib/Drupal/system/Tests/Serialization/EntitySerializationTest.php @@ -120,9 +120,38 @@ public function testSerialize() { $expected = json_encode($normalized); // Test 'json'. $actual = $serializer->serialize($this->entity, 'json'); - $this->assertIdentical($actual, $expected, 'Entity serializes to JSON when json is requested.'); + $this->assertIdentical($actual, $expected, 'Entity serializes to JSON when "json" is requested.'); + $actual = $serializer->serialize($normalized, 'json'); + $this->assertIdentical($actual, $expected, 'A normalized array serializes to JSON when "json" is requested'); // Test 'ajax'. $actual = $serializer->serialize($this->entity, 'ajax'); - $this->assertIdentical($actual, $expected, 'Entity serializes to JSON when ajax is requested.'); + $this->assertIdentical($actual, $expected, 'Entity serializes to JSON when "ajax" is requested.'); + $actual = $serializer->serialize($normalized, 'ajax'); + $this->assertIdentical($actual, $expected, 'A normalized array serializes to JSON when "ajax" is requested'); + + // Generate the expected xml in a way that allows changes to entity property + // order. + $expected = array( + 'id' => '<id><value>' . $this->entity->id() . '</value></id>', + 'revision_id' => '<revision_id><value>' . $this->entity->getRevisionId() . '</value></revision_id>', + 'uuid' => '<uuid><value>' . $this->entity->uuid() . '</value></uuid>', + 'langcode' => '<langcode><value>' . LANGUAGE_NOT_SPECIFIED . '</value></langcode>', + 'default_langcode' => '<default_langcode><value/></default_langcode>', + 'name' => '<name><value>' . $this->values['name'] . '</value></name>', + 'user_id' => '<user_id><value>' . $this->values['user_id'] . '</value></user_id>', + 'field_test_text' => '<field_test_text><value>' . $this->values['field_test_text']['value'] . '</value><format>' . $this->values['field_test_text']['format'] . '</format></field_test_text>', + ); + // Sort it in the same order as normalised. + $expected = array_merge($normalized, $expected); + // Add header and footer. + array_unshift($expected, '<?xml version="1.0"?>' . PHP_EOL . '<response>'); + $expected[] = '</response>' . PHP_EOL; + // Reduced the array to a string. + $expected = implode('', $expected); + // Test 'xml'. The output should match that of Symfony's XmlEncoder. + $actual = $serializer->serialize($this->entity, 'xml'); + $this->assertIdentical($actual, $expected); + $actual = $serializer->serialize($normalized, 'xml'); + $this->assertIdentical($actual, $expected); } } -- GitLab