Sf2:FOS用户包:注册AJAX

Sf2:FOS用户包:注册AJAX,ajax,symfony,listener,fosuserbundle,Ajax,Symfony,Listener,Fosuserbundle,我正在尝试用AJAX注册一个用户 我在FOSUserEvents::REGISTRATION\u SUCCESS 所以我想知道是否已经发出了AJAX请求,但是客户端的响应并不能让我满意 这里是我的事件侦听器,请注意,发送的响应是一个测试,因此当然不应该有“其他”条件 <?php namespace SE\AppBundle\EventListener; use FOS\UserBundle\FOSUserEvents; use FOS\UserBundle\Event\FormEven

我正在尝试用AJAX注册一个用户

我在
FOSUserEvents::REGISTRATION\u SUCCESS

所以我想知道是否已经发出了AJAX请求,但是客户端的响应并不能让我满意

这里是我的事件侦听器,请注意,发送的响应是一个测试,因此当然不应该有“其他”条件

<?php

namespace SE\AppBundle\EventListener;

use FOS\UserBundle\FOSUserEvents;
use FOS\UserBundle\Event\FormEvent;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\HttpFoundation\RedirectResponse;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpFoundation\RequestStack;

/**
 * Ajax listener on FOS UserBundle registration
 */
class RegistrationListener implements EventSubscriberInterface
{
    private $router;

    public function __construct(RequestStack $RequestStack)
    {
        $this->requestStack = $RequestStack;
    }

    /**
     * {@inheritDoc}
     */
    public static function getSubscribedEvents()
    {
        return array(
            FOSUserEvents::REGISTRATION_SUCCESS => 'onRegistrationSuccess'
        );
    }

    public function onRegistrationSuccess()
    {

        $request = $this->requestStack->getCurrentRequest();

        if ($request->isXmlHttpRequest()) {

            $array = array( 'success' => true ); // data to return via JSON
            $response = new Response( json_encode( $array ) );
            $response->headers->set( 'Content-Type', 'application/json' );

            return $response;

        }
        else{
            $array = array( 'success' => false ); // data to return via JSON
            $response = new Response( json_encode( $array ) );
            $response->headers->set( 'Content-Type', 'application/json' );

            return $response;
        }
    }
}
javascript:

// Submit the request
$.ajax({
    type        : 'POST',
    url         : url,
    data        : data,
    success     : function(data, status, object) {

        console.log('success');
        console.log(data);

    },
    error: function(data, status, object){
        console.log('error');
        console.log(data);
    }
});
首先,奇怪的是它处于错误状态

<?php

namespace SE\AppBundle\EventListener;

use FOS\UserBundle\FOSUserEvents;
use FOS\UserBundle\Event\FormEvent;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\HttpFoundation\RedirectResponse;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpFoundation\RequestStack;

/**
 * Ajax listener on FOS UserBundle registration
 */
class RegistrationListener implements EventSubscriberInterface
{
    private $router;

    public function __construct(RequestStack $RequestStack)
    {
        $this->requestStack = $RequestStack;
    }

    /**
     * {@inheritDoc}
     */
    public static function getSubscribedEvents()
    {
        return array(
            FOSUserEvents::REGISTRATION_SUCCESS => 'onRegistrationSuccess'
        );
    }

    public function onRegistrationSuccess()
    {

        $request = $this->requestStack->getCurrentRequest();

        if ($request->isXmlHttpRequest()) {

            $array = array( 'success' => true ); // data to return via JSON
            $response = new Response( json_encode( $array ) );
            $response->headers->set( 'Content-Type', 'application/json' );

            return $response;

        }
        else{
            $array = array( 'success' => false ); // data to return via JSON
            $response = new Response( json_encode( $array ) );
            $response->headers->set( 'Content-Type', 'application/json' );

            return $response;
        }
    }
}
console.log
(数据)返回注册成功页面的DOM:

...
<p>Congrats brieuc.tribouillet7777@gmail.com, your account is now activated.</p> 
...
。。。
祝贺布里欧克。tribouillet7777@gmail.com,您的帐户现在已激活。

...

那么这个逻辑应该在这里,还是应该重写控制器?我做错了什么?

由于
注册成功
事件的级别,您不能直接从
事件监听器返回响应

您需要获取
FormEvent
并修改其响应。
让我们将其作为参数传递:

class RegistrationListener implements EventSubscriberInterface
{
    // ...

    public function onRegistrationSuccess(FormEvent $event)
    {
        $request = $this->requestStack->getCurrentRequest();

        // Prepare your response
        if ($request->isXmlHttpRequest()) {
            $array = array( 'success' => true ); // data to return via JSON
            $response = new Response( json_encode( $array ) );
            $response->headers->set( 'Content-Type', 'application/json' );
        } else {
            $array = array( 'success' => false ); // data to return via JSON
            $response = new Response( json_encode( $array ) );
            $response->headers->set( 'Content-Type', 'application/json' );
        }

        // Send it
        $event->setResponse($response);
    }
}
它应该会起作用

注意此事件存在无法修改响应的问题。
如果出现问题,您需要在事件订阅中设置低优先级:

public static function getSubscribedEvents()
{
    return [
        FOSUserEvents::REGISTRATION_SUCCESS => [
            ['onRegistrationSuccess', -10],
        ],
    ];
}

编辑

注意您应该使用JsonResponse而不是
json\u encode
对数据进行编码,并手动设置
内容类型

要获取表单本身及其最终错误,可以执行以下操作:

public function onRegistrationSuccess(FormEvent $event)
{
    $form = $event->getForm();

    if (count($validationErrors = $form->getErrors()) == 0) {
        return $event->setResponse(new JsonResponse(['success' => true]));
    }

    // There is some errors, prepare a failure response
    $body = [];

    // Add the errors in your response body
    foreach ($validationErrors as $error) {
        $body[] = [
            'property' => $error->getPropertyPath() // The field
            'message'  => $error->getMessage() // The error message
        ];
    }

    // Set the status to Bad Request in order to grab it in front (i.e $.ajax({ ...}).error(...))
    $response = new JsonResponse($body, 400); 
    $event->setResponse($response);
}

但是因为这是一个成功的事件,您可能需要重写该方法本身。

太棒了!因此,以这种方式使用事件侦听器比重写该方法要好,不是吗?您是否也能捕获fos用户事件之一中的表单错误?请查看我的编辑:),这完全取决于事件,我认为没有注册失败事件,因此在这种情况下,您可能需要覆盖该方法。