Reputation: 18729
I am working on a Symfony 2 WebApp that provides a JSON webservice to communicate with mobile apps on different platforms (iOS, Android, etc.).
The WebApp uses the FOS RestBundle to process and deserialize the received the JSON data:
# app/config/config.yml
sensio_framework_extra:
request: { converters: true }
fos_rest:
...
body_converter:
enabled: true
/**
* Sync Controller implementation
* @ParamConverter("post", converter="fos_rest.request_body")
*/
public function syncAction(SyncBag $syncBag) {
// ...
}
/**
* Sync Data Wrapper
*/
public class SyncBag {
...
/**
* @JMS\Type("DateTime<'Y-m-d'>")
*/
private $startDate;
}
This works quite well. The Problem: Some of the mobile Apps use a wrong date format to send some of the data: While the WebApp expects "Y-m-d" the mobile Apps send "Y-m-d H:i:s". This leads to an exception:
Uncaught PHP Exception Symfony\Component\HttpKernel\Exception\BadRequestHttpException: "Invalid datetime "2016-03-04 12:00:00", expected format Y-m-d." at /.../vendor/friendsofsymfony/rest-bundle/FOS/RestBundle/Request/AbstractRequestBodyParamConverter.php line 113
Of course updating the mobile apps to use/send the correct date format is the correct solution for this error. But implementing and publishing this bugfix will take quite a while. Passing Apples review will take some time. Waiting for the users to update the latest version will take some time. And so on.
On the other hand the problem could quite easily be solved by updating the deserializing process in the WebApp.
Question: Is it somehow possible to hook into the deserializing process within the FOS RestBundle ParamConverter? If I could filter/clean the request (simpley search/replace wrong date formats) before the data is handled by the Converter, the problem could be solved within minutes.
Any idea/suggestion how to do this?
Thanks!
Upvotes: 0
Views: 391
Reputation: 2889
You're can create event listener for pre deserialize event
This is dispatched before an object is deserialized. You can use this to modify submitted data, or modify the type that is being used for deserialization.
Also, you're can create listener for kernel.request (or for kernel.controller with priority bigger than param converter listener priotity) event, and filter data as need.
Upvotes: 1
Reputation: 4089
Why not create your own ParamConverter extending/using what you need from the existing ones (e.g. in your case from the built in DateTime ParamConverter, see documentation)
You can even set a priority for ParamConverters to be sure one is executed before another.
Or is there anything special you'd like to achieve here?
Upvotes: 1