【问题标题】:Symfony2 embed all FOSUserBundle formsSymfony2 嵌入所有 FOSUserBundle 表单
【发布时间】:2014-03-19 13:43:44
【问题描述】:

我正在尝试将所有 FOSUserBundle 表单嵌入到布局左侧的边栏中。

这是我的src/My/MainBundle/Resources/config/routing.yml

index:
    pattern: /
    defaults: { _controller: MyMainBundle:Main:index }

login:
    pattern: /login
    defaults: { _controller: MyMainBundle:Main:index }

resetting_request:
    pattern: /resetting/request
    defaults: { _controller: MyMainBundle:Main:index }

resetting_send_email:
    pattern: /resetting/send-email
    defaults: { _controller: MyMainBundle:Main:index }

src/My/MainBundle/Resources/views/layout.html.twig,我有(除其他外):

<div id="sidebar">
    {% if is_granted('IS_AUTHENTICATED_REMEMBERED') %}
        <p>You are logged in blah blah blah</p>
    {% elseif app.request.attributes.get('_route') == 'resetting_request' %}
        {{ render(controller('FOSUserBundle:Resetting:request')) }}
    {% elseif app.request.attributes.get('_route') == 'resetting_send_email' %}
        {{ render(controller('FOSUserBundle:Resetting:sendEmail')) }}
    {% else %}
        {{ render(controller('FOSUserBundle:Security:login')) }}
    {% endif %}
</div>

登录表单工作正常,它提交到 /login_check,然后重定向到请求的页面,如果登录名和密码正确,或者,如果登录名或密码错误,它重定向到 /login(在那个如果它在侧边栏中正确显示表单,并带有相应的错误消息)。

我遇到了“忘记密码?”的问题不过形式。

它显示在侧边栏中,并提交到 /resetting/send-email,但随后它不会重定向到任何东西。然后它告诉我用户名或电子邮件“”不存在。

如果我评论“resetting_send_email”路由,那么“send email”操作有效,但输出不在侧边栏中(事实上,它周围甚至没有布局)。

有什么想法吗?

【问题讨论】:

  • 您是否在会话处理程序中使用 PDO?
  • 不,我使用的是默认会话处理程序。
  • 我刚刚意识到您的问题。看答案..

标签: forms symfony fosuserbundle


【解决方案1】:

FOSUserBundle:Resetting:sendEmail 期望用户名或电子邮件作为 POST。

public function sendEmailAction(Request $request)
{
    $username = $request->request->get('username');

    /** @var $user UserInterface */
    $user = $this->container->get('fos_user.user_manager')
                ->findUserByUsernameOrEmail($username);

    if (null === $user) {
        return $this->container->get('templating')->renderResponse('bla blah');
    }

当您渲染控制器时,您会在没有 POST 的情况下向控制器发出新请求,因此没有电子邮件或用户名。

如果没有 POST,脚本无法找到 user,这意味着它在第一次检查时中断。

【讨论】:

    【解决方案2】:

    我尝试使用controller events,但还不够。

    我必须override the FOSUserBundle controllers

    所以,我创建了一个新的包 (MyUserBundle),FOSUserBundle 的子项,如链接中所述,这是我的控制器:

    // src/My/UserBundle/Controller/ResettingController.php
    
    namespace My\UserBundle\Controller;
    
    use \Symfony\Component\HttpFoundation\Request;
    use FOS\UserBundle\Controller\ResettingController as BaseController;
    use Symfony\Component\HttpFoundation\RedirectResponse;
    
    class ResettingController extends BaseController
    {
        /**
         * Request reset user password: submit form and send email
         */
        public function sendEmailAction(Request $request)
        {
            //$username = $request->request->get('username'); // Since this action was called in a twig file by a "{{ render(controller(...)) }}", the "request" attribute is empty.
            $username = $_POST['username']; // But $_POST still works
    
            /** @var $user UserInterface */
            $user = $this->container->get('fos_user.user_manager')->findUserByUsernameOrEmail($username);
    
            if (null === $user) {
                return $this->container->get('templating')->renderResponse('FOSUserBundle:Resetting:request.html.'.$this->getEngine(), array('invalid_username' => $username));
            }
    
            if ($user->isPasswordRequestNonExpired($this->container->getParameter('fos_user.resetting.token_ttl'))) {
                return $this->container->get('templating')->renderResponse('FOSUserBundle:Resetting:passwordAlreadyRequested.html.'.$this->getEngine());
            }
    
            if (null === $user->getConfirmationToken()) {
                /** @var $tokenGenerator \FOS\UserBundle\Util\TokenGeneratorInterface */
                $tokenGenerator = $this->container->get('fos_user.util.token_generator');
                $user->setConfirmationToken($tokenGenerator->generateToken());
            }
    
            $this->container->get('fos_user.mailer')->sendResettingEmailMessage($user);
            $user->setPasswordRequestedAt(new \DateTime());
            $this->container->get('fos_user.user_manager')->updateUser($user);
    
            //return new RedirectResponse($this->container->get('router')->generate('fos_user_resetting_check_email',
            //    array('email' => $this->getObfuscatedEmail($user))
            //)); // Throws an exception (because this action was called by a "{{ render(controller(..)) }}").
    
            //header('Location: '.$this->container->get('router')->generate('fos_user_resetting_check_email', array('email' => $this->getObfuscatedEmail($user))));
            //exit; // The redirect works, but the "exit" prevents the email from being sent
    
            return new \Symfony\Component\HttpFoundation\Response(
                '<script type="text/javascript">window.location = "'.$this->container->get('router')->generate('fos_user_resetting_check_email', array('email' => $this->getObfuscatedEmail($user))).'"</script>'
            );
        }
    }
    

    在我的layout.html.twig,我替换了

    {{ render(controller('FOSUserBundle:Resetting:sendEmail')) }}
    

    通过

    {{ render(controller('MyUserBundle:Resetting:sendEmail')) }}
    

    我现在将在边栏中嵌入“check_email”操作,以及 FOSUserBundle 中的其他表单/模板。

    【讨论】:

      【解决方案3】:

      评论不是最简单的

          <requirement key="_method">POST</requirement>
      

      进入

          <!-- <requirement key="_method">POST</requirement> --> 
      

      在 /Resources/config/routing/resetting.xml 中?

      由于传递的唯一信息是用户名(无论如何都可以公开获得),我“希望”我不会在这里让自己面临隐藏的风险。

      我有同样的问题,评论成功了(感谢用户的 3409662 cmets)。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2013-08-27
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多