Advertisement
airux

Untitled

Aug 16th, 2018
61
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 6.21 KB | None | 0 0
  1. <?php
  2.  
  3. /*
  4. * This file is part of the FOSRestBundle package.
  5. *
  6. * (c) FriendsOfSymfony <http://friendsofsymfony.github.com/>
  7. *
  8. * For the full copyright and license information, please view the LICENSE
  9. * file that was distributed with this source code.
  10. */
  11.  
  12. namespace FOS\RestBundle\Request;
  13.  
  14. use FOS\RestBundle\Context\Context;
  15. use FOS\RestBundle\Serializer\Serializer;
  16. use JMS\Serializer\Exception\Exception as JMSSerializerException;
  17. use JMS\Serializer\Exception\UnsupportedFormatException;
  18. use Sensio\Bundle\FrameworkExtraBundle\Configuration\ParamConverter;
  19. use Sensio\Bundle\FrameworkExtraBundle\Request\ParamConverter\ParamConverterInterface;
  20. use Symfony\Component\HttpFoundation\Request;
  21. use Symfony\Component\HttpKernel\Exception\BadRequestHttpException;
  22. use Symfony\Component\HttpKernel\Exception\UnsupportedMediaTypeHttpException;
  23. use Symfony\Component\OptionsResolver\OptionsResolver;
  24. use Symfony\Component\Serializer\Exception\ExceptionInterface as SymfonySerializerException;
  25. use Symfony\Component\Validator\Validator\ValidatorInterface;
  26.  
  27. /**
  28. * @author Tyler Stroud <tyler@tylerstroud.com>
  29. */
  30. class RequestBodyParamConverter implements ParamConverterInterface
  31. {
  32. private $serializer;
  33. private $context = [];
  34. private $validator;
  35.  
  36. /**
  37. * The name of the argument on which the ConstraintViolationList will be set.
  38. *
  39. * @var null|string
  40. */
  41. private $validationErrorsArgument;
  42.  
  43. /**
  44. * @param Serializer $serializer
  45. * @param array|null $groups An array of groups to be used in the serialization context
  46. * @param string|null $version A version string to be used in the serialization context
  47. * @param ValidatorInterface $validator
  48. * @param string|null $validationErrorsArgument
  49. *
  50. * @throws \InvalidArgumentException
  51. */
  52. public function __construct(
  53. Serializer $serializer,
  54. $groups = null,
  55. $version = null,
  56. ValidatorInterface $validator = null,
  57. $validationErrorsArgument = null
  58. ) {
  59. $this->serializer = $serializer;
  60.  
  61. if (!empty($groups)) {
  62. $this->context['groups'] = (array) $groups;
  63. }
  64.  
  65. if (!empty($version)) {
  66. $this->context['version'] = $version;
  67. }
  68.  
  69. if (null !== $validator && null === $validationErrorsArgument) {
  70. throw new \InvalidArgumentException('"$validationErrorsArgument" cannot be null when using the validator');
  71. }
  72.  
  73. $this->validator = $validator;
  74. $this->validationErrorsArgument = $validationErrorsArgument;
  75. }
  76.  
  77. /**
  78. * {@inheritdoc}
  79. */
  80. public function apply(Request $request, ParamConverter $configuration)
  81. {
  82. $options = (array) $configuration->getOptions();
  83.  
  84. if (isset($options['deserializationContext']) && is_array($options['deserializationContext'])) {
  85. $arrayContext = array_merge($this->context, $options['deserializationContext']);
  86. } else {
  87. $arrayContext = $this->context;
  88. }
  89. $this->configureContext($context = new Context(), $arrayContext);
  90.  
  91. try {
  92. $object = $this->serializer->deserialize(
  93. $request->getContent(),
  94. $configuration->getClass(),
  95. $request->getContentType(),
  96. $context
  97. );
  98. } catch (UnsupportedFormatException $e) {
  99. return $this->throwException(new UnsupportedMediaTypeHttpException($e->getMessage(), $e), $configuration);
  100. } catch (JMSSerializerException $e) {
  101. return $this->throwException(new BadRequestHttpException($e->getMessage(), $e), $configuration);
  102. } catch (SymfonySerializerException $e) {
  103. return $this->throwException(new BadRequestHttpException($e->getMessage(), $e), $configuration);
  104. }
  105.  
  106. $request->attributes->set($configuration->getName(), $object);
  107.  
  108. if (null !== $this->validator && (!isset($options['validate']) || $options['validate'])) {
  109. $validatorOptions = $this->getValidatorOptions($options);
  110.  
  111. $errors = $this->validator->validate($object, null, $validatorOptions['groups']);
  112.  
  113. $request->attributes->set(
  114. $this->validationErrorsArgument,
  115. $errors
  116. );
  117. }
  118.  
  119. return true;
  120. }
  121.  
  122. /**
  123. * {@inheritdoc}
  124. */
  125. public function supports(ParamConverter $configuration)
  126. {
  127. return null !== $configuration->getClass() && 'fos_rest.request_body' === $configuration->getConverter();
  128. }
  129.  
  130. /**
  131. * @param Context $context
  132. * @param array $options
  133. */
  134. protected function configureContext(Context $context, array $options)
  135. {
  136. foreach ($options as $key => $value) {
  137. if ('groups' === $key) {
  138. $context->addGroups($options['groups']);
  139. } elseif ('version' === $key) {
  140. $context->setVersion($options['version']);
  141. } elseif ('maxDepth' === $key) {
  142. @trigger_error('Context attribute "maxDepth" is deprecated since version 2.1 and will be removed in 3.0. Use "enable_max_depth" instead.', E_USER_DEPRECATED);
  143. $context->setMaxDepth($options['maxDepth']);
  144. } elseif ('enableMaxDepth' === $key) {
  145. $context->enableMaxDepth($options['enableMaxDepth']);
  146. } elseif ('serializeNull' === $key) {
  147. $context->setSerializeNull($options['serializeNull']);
  148. } else {
  149. $context->setAttribute($key, $value);
  150. }
  151. }
  152. }
  153.  
  154. /**
  155. * Throws an exception or return false if a ParamConverter is optional.
  156. */
  157. private function throwException(\Exception $exception, ParamConverter $configuration)
  158. {
  159. if ($configuration->isOptional()) {
  160. return false;
  161. }
  162.  
  163. throw $exception;
  164. }
  165.  
  166. /**
  167. * @param array $options
  168. *
  169. * @return array
  170. */
  171. private function getValidatorOptions(array $options)
  172. {
  173. $resolver = new OptionsResolver();
  174. $resolver->setDefaults([
  175. 'groups' => null,
  176. 'traverse' => false,
  177. 'deep' => false,
  178. ]);
  179.  
  180. return $resolver->resolve(isset($options['validator']) ? $options['validator'] : []);
  181. }
  182. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement