How can I send JSON response in symfony2 controller

后端 未结 5 1735
栀梦
栀梦 2020-12-04 11:02

I am using jQuery to edit my form which is built in Symfony.

I am showing the form in jQuery dialog and then submitting it.

相关标签:
5条回答
  • 2020-12-04 11:27

    Symfony 2.1

    $response = new Response(json_encode(array('name' => $name)));
    $response->headers->set('Content-Type', 'application/json');
    
    return $response;
    

    Symfony 2.2 and higher

    You have special JsonResponse class, which serialises array to JSON:

    return new JsonResponse(array('name' => $name));
    

    But if your problem is How to serialize entity then you should have a look at JMSSerializerBundle

    Assuming that you have it installed, you'll have simply to do

    $serializedEntity = $this->container->get('serializer')->serialize($entity, 'json');
    
    return new Response($serializedEntity);
    

    You should also check for similar problems on StackOverflow:

    • How to encode Doctrine entities to JSON in Symfony 2.0 AJAX application?
    • Symfony 2 Doctrine export to JSON
    0 讨论(0)
  • 2020-12-04 11:29

    If your data is already serialized:

    a) send a JSON response

    public function someAction()
    {
        $response = new Response();
        $response->setContent(file_get_contents('path/to/file'));
        $response->headers->set('Content-Type', 'application/json');
        return $response;
    }
    

    b) send a JSONP response (with callback)

    public function someAction()
    {
        $response = new Response();
        $response->setContent('/**/FUNCTION_CALLBACK_NAME(' . file_get_contents('path/to/file') . ');');
        $response->headers->set('Content-Type', 'text/javascript');
        return $response;
    }
    

    If your data needs be serialized:

    c) send a JSON response

    public function someAction()
    {
        $response = new JsonResponse();
        $response->setData([some array]);
        return $response;
    }
    

    d) send a JSONP response (with callback)

    public function someAction()
    {
        $response = new JsonResponse();
        $response->setData([some array]);
        $response->setCallback('FUNCTION_CALLBACK_NAME');
        return $response;
    }
    

    e) use groups in Symfony 3.x.x

    Create groups inside your Entities

    <?php
    
    namespace Mindlahus;
    
    use Symfony\Component\Serializer\Annotation\Groups;
    
    /**
     * Some Super Class Name
     *
     * @ORM    able("table_name")
     * @ORM\Entity(repositoryClass="SomeSuperClassNameRepository")
     * @UniqueEntity(
     *  fields={"foo", "boo"},
     *  ignoreNull=false
     * )
     */
    class SomeSuperClassName
    {
        /**
         * @Groups({"group1", "group2"})
         */
        public $foo;
        /**
         * @Groups({"group1"})
         */
        public $date;
    
        /**
         * @Groups({"group3"})
         */
        public function getBar() // is* methods are also supported
        {
            return $this->bar;
        }
    
        // ...
    }
    

    Normalize your Doctrine Object inside the logic of your application

    <?php
    
    use Symfony\Component\HttpFoundation\Response;
    use Symfony\Component\Serializer\Mapping\Factory\ClassMetadataFactory;
    // For annotations
    use Doctrine\Common\Annotations\AnnotationReader;
    use Symfony\Component\Serializer\Mapping\Loader\AnnotationLoader;
    use Symfony\Component\Serializer\Serializer;
    use Symfony\Component\Serializer\Normalizer\ObjectNormalizer;
    use Symfony\Component\Serializer\Encoder\JsonEncoder;
    
    ...
    
    $repository = $this->getDoctrine()->getRepository('Mindlahus:SomeSuperClassName');
    $SomeSuperObject = $repository->findOneById($id);
    
    $classMetadataFactory = new ClassMetadataFactory(new AnnotationLoader(new AnnotationReader()));
    $encoder = new JsonEncoder();
    $normalizer = new ObjectNormalizer($classMetadataFactory);
    $callback = function ($dateTime) {
        return $dateTime instanceof \DateTime
            ? $dateTime->format('m-d-Y')
            : '';
    };
    $normalizer->setCallbacks(array('date' => $callback));
    $serializer = new Serializer(array($normalizer), array($encoder));
    $data = $serializer->normalize($SomeSuperObject, null, array('groups' => array('group1')));
    
    $response = new Response();
    $response->setContent($serializer->serialize($data, 'json'));
    $response->headers->set('Content-Type', 'application/json');
    return $response;
    
    0 讨论(0)
  • 2020-12-04 11:36

    Since Symfony 3.1 you can use JSON Helper http://symfony.com/doc/current/book/controller.html#json-helper

    public function indexAction()
    {
    // returns '{"username":"jane.doe"}' and sets the proper Content-Type header
    return $this->json(array('username' => 'jane.doe'));
    
    // the shortcut defines three optional arguments
    // return $this->json($data, $status = 200, $headers = array(), $context = array());
    }
    
    0 讨论(0)
  • 2020-12-04 11:44

    Symfony 2.1 has a JsonResponse class.

    return new JsonResponse(array('name' => $name));
    

    The passed in array will be JSON encoded the status code will default to 200 and the content type will be set to application/json.

    There is also a handy setCallback function for JSONP.

    0 讨论(0)
  • 2020-12-04 11:48

    To complete @thecatontheflat answer I would recommend to also wrap your action inside of a try … catch block. This will prevent your JSON endpoint from breaking on exceptions. Here's the skeleton I use:

    public function someAction()
    {
        try {
    
            // Your logic here...
    
            return new JsonResponse([
                'success' => true,
                'data'    => [] // Your data here
            ]);
    
        } catch (\Exception $exception) {
    
            return new JsonResponse([
                'success' => false,
                'code'    => $exception->getCode(),
                'message' => $exception->getMessage(),
            ]);
    
        }
    }
    

    This way your endpoint will behave consistently even in case of errors and you will be able to treat them right on a client side.

    0 讨论(0)
提交回复
热议问题