MatiRC
MatiRC

Reputation: 339

How to handle correctly JSON request in symfony?

I'm trying to handle this problem: My app send JSON POST request with several information encoded in a Json. Example:

{"UserInfoA":{"1":123,"2":"hello","3":"bye","4":{"subinfo":1,"subinfo2":10}},
 "UserInfoB":{"a":"12345678","b":"asd"}} // and so on...

each UserInfo have:

So, to achieve this problem I did another controller like JsonHandler, which receive this request and then forward to each controller after gut this JSON into differents objects. Example:

public function getJson (Request $request){
    if (0 === strpos($request->headers->get('Content-Type'), 'application/json')) {
                $data = json_decode($request->getContent(), true);
            }
    if (!isset($data['UserInfoA'])){
         return new JsonResponse('ERROR');
              }
    $uia = $data['UserInfoA'];
    $idInfoA = $this->forward('Path::dataAPersist',array('data'=>$uia));
        }
    // same with userinfoB and other objects
    return $idInfoA ;

This works perfectly but Is it correct? Should i use services instead?

EDIT : I need to response the ID in a Json and this->forward returns a Response, so i can't use JsonResponse and if a send directly $idInfoA just send the IDNUMBER not in a JSON, how can i do it?

To sum up : a Json listener that receive the information, work it and then dispatch to the corresponding controller. This listener, should be a controller, a service or another thing?

Upvotes: 8

Views: 47051

Answers (5)

Just Pilot
Just Pilot

Reputation: 624

With Symfony 6 just use the getPayload() method.

Example:

$request->getPayload()->get('email')

It is as simple as it sounds.

Upvotes: 6

PhoneixS
PhoneixS

Reputation: 11016

Since Symfony 5.2, you can do a $data = $request->toArray();. With this, you would have an associative array with the JSON content parsed.

For example, with the next content:

{
  "id": 123,
  "name": "Someone"
}

You can have:

...
public function doSomething(Request $request) {
  $data = $request->toArray();
  $id = $data['id'];
  $name = $data['name'];
  doSomethingInteresting($name, $id);
}
...

Upvotes: 3

Juan I. Morales Pestana
Juan I. Morales Pestana

Reputation: 1147

I recommend the use of symfony-bundles/json-request-bundle since it does the JsonRequestTransformerListener for you. You just need to recieve the request parameters as usual:

...
$request->get('some_parameter');
...

Upvotes: 12

Barkati.med
Barkati.med

Reputation: 630

hi you have to use service to make the Transformation

class php

use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpKernel\Event\GetResponseEvent;

class JsonRequestTransformerListener {


public function onKernelRequest(GetResponseEvent $event) {
    $request = $event->getRequest();
    $content = $request->getContent();
    if (empty($content)) {
        return;
    }
    if (!$this->isJsonRequest($request)) {
        return;
    }
    if (!$this->transformJsonBody($request)) {
        $response = Response::create('Unable to parse request.', 400);
        $event->setResponse($response);
    }
}


private function isJsonRequest(Request $request) {
    return 'json' === $request->getContentType();
}


private function transformJsonBody(Request $request) {
    $data = json_decode($request->getContent(), true);
    if (json_last_error() !== JSON_ERROR_NONE) {
        return false;
    }
    if ($data === null) {
        return true;
    }
    $request->request->replace($data);
    return true;
}
 }

And In Your Service.yml

    kernel.event_listener.json_request_transformer:
    class: You\NameBundle\Service\JsonRequestTransformerListener
    tags:
        - { name: "kernel.event_listener", event: "kernel.request",method: "onKernelRequest", priority: "100" }

Now You can call The Default request function to get Data

$request->request->all();

Upvotes: 7

Amirhosein Zlf
Amirhosein Zlf

Reputation: 31

You can use symfony ParamConverter to to convert the json into any object you want and raise a meaningful Exception if anything goes wrong.

You can add custom ParamConverters and use them in your actions with annotation

Upvotes: 3

Related Questions