Параметр symfony2 _target_path в заголовке запроса повторяет app_dev.php

0

Я использую следующий код для генерации перенаправления после успешного входа в систему:

$request->request->set('_target_path', $this->router->generate('renew_subscription'));

Выходной URL:

http://mysite.dev/app_dev.php/app_dev.php/renew_subscription

Как я могу убедиться, что app_dev.php не повторяется дважды? Я чувствую, что str_replace не будет достаточно чистым.

РЕДАКТИРОВАТЬ:

Я устанавливаю это в прослушивателе входа. Я понял, что обработчик входа в систему не работает, потому что служба securitymanager еще не была инициирована:

portfolio_change_and_login_listener:
    class: %portfolio_change_and_login_listener.class%
    arguments: [@security.authorization_checker, @doctrine.orm.entity_manager, @session, @security_manager, @router]
    tags:
        - { name: kernel.event_listener, event: portfolio_change, method: onPortfolioUserChange }
        - { name: kernel.event_listener, event: security.interactive_login, method: onSecurityInteractiveLogin, priority: 255 }

Благодаря !

  • 0
    Где вы это устанавливаете?
  • 0
    Я устанавливаю это в прослушивателе входа.
Теги:
login

4 ответа

2

вместо set _target_paath в вашем контроллере или службе вы можете установить его в виде формы:

добавьте это поле в свою форму для входа:

<input type="hidden" name="_target_path" value="YourRouteName" />

"YourRouteName" - это название вашего маршрута

  • 0
    не применимо к моему случаю, я устанавливаю это из прослушивателя входа в систему
0

Попробуйте использовать Absolute URL вместо Relative.

$request = $event->getRequest();
$route = $this->router->generate('your_url', [], UrlGeneratorInterface::ABSOLUTE_URL)
$request->request->set('_target_path', $route);

Документация https://symfony.com/doc/current/routing.html#generating-absolute-urls

0

Таким образом, есть хороший способ сделать перенаправление, используя обработчик входа. См. Ответ Б. Рад.

Я искал способ сделать это изнутри регистратора входа в систему, потому что когда вы создаете экземпляр обработчика входа, токен еще не заполнен пользователем. Он заполняется только после вызова функции onAuthenticationSuccess. У меня была зависимость от пользователя, и я сначала загрузил его с помощью конструктора, он не работал. Использование setter и вызов depedency изнутри onAuthenticationSuccess было решением

В любом случае, мы также можем сделать переадресацию из регистратора входа в систему, используя:

$request = $event->getRequest();
$route = strreplace('app_dev.php', '', $this->router->generate('your_route'))
$request->request->set('_target_path', $route );
0

Вы должны установить контроллер и использовать RedirectResponse

Это слушатель, который я использую, чтобы следующий маршрут был запланированным следующим шагом в форме, чтобы пользователи не могли прыгать. Я проверяю, если

use Doctrine\ORM\EntityManager;
use Symfony\Component\HttpFoundation\RedirectResponse;
use Symfony\Component\HttpKernel\Exception\AccessDeniedHttpException;
use Symfony\Component\HttpKernel\Event\FilterControllerEvent;
use Symfony\Component\Security\Core\Authentication\Token\Storage\TokenStorageInterface;

class SampleListener
{
    protected $em;
    protected $token_storage;
    private $router;

    function __construct(TokenStorageInterface $token_storage, EntityManager $em, $router)
    {
        $this->token_storage = $token_storage;
        $this->em = $em;
        $this->router = $router;
    }

    public function onKernelController(FilterControllerEvent $event)
    {

        //some other checks go here

        $route = $event->getRequest()->attributes->get("_route");
        $appStep = $app->getAppStep();


        if ($route != $appStep) {
            //Check to see if the route is going to the planned next stp
            $stepsVisited = explode(",", $app->getVisited());
            if (in_array($route, $stepsVisited)) {
                //if its not going to the next planned step then make sure its a path we visited before.
                return;

            } else {

                $url = $this->router->generate($appStep, array("appId" => $appId));
                $event->setController(function () use ($url) {
                    return new RedirectResponse($url);
                });
            }
        }
    }
}

Подменю Variable - это просто ссылка на имя маршрута, например, место, как показано ниже.

/**
 * @Route("/place/{appId}", name="Place")
 */

Вот как выглядит мой сервис. Это делается в yml

sample.action_listener:
        class: Bundle\Name\EventListener\AppSecurityListener
        arguments:
            - @security.token_storage
            - @doctrine.orm.entity_manager
            - @router
        tags:
            - { name: kernel.event_listener, event: kernel.controller, method: onKernelController }

Надеюсь это поможет. Дайте знать, если у вас появятся вопросы.


Редактировать 1

Если вы пытаетесь запустить перенаправление после входа в систему, вы должны использовать обработчик, как это.

use Symfony\Component\Security\Http\Authentication\AuthenticationSuccessHandlerInterface;
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
use Symfony\Component\Security\Core\SecurityContext;
use Symfony\Component\Security\Core\Security;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\RedirectResponse;
use Symfony\Component\Routing\Router;

class LoginSuccessHandler implements AuthenticationSuccessHandlerInterface
{

    protected $router;
    protected $security;

    public function __construct(Router $router, SecurityContext $security)
    {
        $this->router = $router;
        $this->security = $security;
    }

    public function onAuthenticationSuccess(Request $request, TokenInterface $token)
    {

        if ($this->security->isGranted('ROLE_ADMIN')) {
            $response = new RedirectResponse($this->router->generate('AnnotationName 4'));
        } elseif ($this->security->isGranted('ROLE_B')) {
            $response = new RedirectResponse($this->router->generate('AnnotationName1'));
        }
//        elseif ($this->security->isGranted('ROLE_ADMIN'))
//        {
//            // redirect the user to where they were before the login process begun.
//            $referer_url = $request->headers->get('referer');
//
//            $response = new RedirectResponse($referer_url);
//        }
        else {
            $response = new RedirectResponse($this->router->generate('Home'));
        }

        return $response;
    }
}

Затем вам нужно установить параметр и службу в файл служб

parameters:
    bundle_name.service.login_success_handler.class: Bundle\Name\Service\LoginSuccessHandler
services:
    bundle_name.service.login_success_handler:
        class:  %bundle_name.service.login_success_handler.class%
        arguments:  [@router, @security.context]
        tags:
            - { name: 'monolog.logger', channel: 'security' } 

Я не могу вспомнить, где я выясню, как это сделать, но это было после многих оглядевшихся примеров. У меня также есть обработчик выхода, который я получил с того же места. Я уверен, что если вы ищете имя класса, вы найдете пример где-нибудь.

  • 0
    ну, я хочу это перенаправление после проверки входа и успешной аутентификации. Как я могу использовать контроллер здесь, если Symfony обрабатывает проверочную часть?
  • 0
    Вы используете пользовательский пакет FOS или вы просто используете Symfony?
Показать ещё 5 комментариев

Ещё вопросы

Сообщество Overcoder
Наверх
Меню