当前位置: 首页 > 知识库问答 >
问题:

验证过滤器重定向回Laravel中的原始POST请求

申屠新觉
2023-03-14

重定向::客户(登录)似乎只适用于GET请求。也就是说,它将把经过身份验证的用户重定向到原始的预期URL(GET)。

在存在POST请求的情况下,在用户成功登录后,是否有一种方式让auth筛选器继续向URL发布?

一个简单的例子:我想展示一个可供任何人查看的表单。点击submit按钮后,auth过滤器将启动,并将来宾带到登录页面。成功验证后,我希望提交请求(即POST请求)继续。

共有2个答案

司马渝
2023-03-14

在Laravel5.2中,他们实现了中间件组,对于新项目,他们将默认的“web”组应用于整个路由。php文件。

问题是:
在确定路由后调用组中间件,因此仅更改当前请求的方法没有任何效果。

有两种不同的方法使其恢复工作(我建议第2条)

解决方案1:
将会话和预期的url中间件放回内核中的全局中间件阵列。php文件-这很简单,而且可以工作,但有时您的项目旁边有一些REST-API路由,而会话在那里没有任何作用
解决方案2:
将所需的url类放在web组中的ShareErrorsFromSession类之后,并采用如下所示的文件:

// Erase all session keys created to track the intended request
Session::forget('intended');

$response = Route::dispatch($request);
return $response;

通过分派修改后的请求,我们打破了当前的生命周期,并调用了一个新的生命周期,因此使用了正确的路由,并按预期工作。第二种方法也给我们提供了一种可能性,如果你想要的话,只对选定的路由定义预期的url功能

程磊
2023-03-14

我同样希望用原始输入重定向回POST请求。在Laravel中,除了通过GET重定向到预期的URL之外,我找不到一种现有的方法来实现这一点。

我首先按照下面的大纲在Laravel4中解决了这个问题,但发现完全相同的设置在Laravel5中不起作用。遵循Laravel 4的大纲,但不要创建IntenderlServiceProvider,而是创建一个中间件。

  1. 问题是,在Laravel 5中,会话似乎是通过在所有服务提供商之后运行的StartSession启动的

/app/Http/Middleware/intenderl。php

<?php namespace App\Http\Middleware;

use Closure;
use Request;
use Session;

class IntendedUrl {

    /**
     * This loads saved POST input data and changes the method to POST if a visitor tried to access a page
     * but was blocked via an auth filter. Auth filter saves data via the Redirect::guest() and after
     * login it needs to be repopulated to simulate a POST.
     *
     * GET requests also may pass through here. I am less certain if it is required for them but shouldn't hurt
     * and may help load any input data.
     *
     * @param  \Illuminate\Http\Request  $request
     * @param  \Closure  $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {
        // Check to see if we were redirected to this page with the Redirect::intended().
        //      We extended the class to track when the redirect occurs so we know to reload additional request data
        if (Session::has('intended.load')) {
            // intended.load could be set without these being set if we were redirected to the default page
            //      if either exists, both should exist but checking separately to be safe
            if (Session::has('intended.method')) {
                Request::setMethod(Session::get('intended.method'));
            }
            if (Session::has('intended.input')) {
                Request::replace(Session::get('intended.input'));
            }
            // Erase all session keys created to track the intended request
            Session::forget('intended');

            // Laravel 5.2+ uses separate global and route middlewares. Dispatch altered request as the route type changed. *Credit to Munsio in answer below
            return \Route::dispatch($request);
        }

        return $next($request);
    }

}
protected $middleware = [
    'Illuminate\Foundation\Http\Middleware\CheckForMaintenanceMode',
    'Illuminate\Cookie\Middleware\EncryptCookies',
    'Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse',
    'Illuminate\Session\Middleware\StartSession',
    'Illuminate\View\Middleware\ShareErrorsFromSession',

    'App\Http\Middleware\IntendedUrl',
];
  • 同样值得注意的是,我将我的客户服务提供商移动到了新的标准/App/providers,并更改了它们的名称空间

我决定扩展框架以添加此功能。很难详细说明我的完整解决方案,但这里有一个概要。要做到这一点,您需要非常熟悉该框架,并阅读如何扩展它。http://laravel.com/docs/extending#ioc-基于扩展

我还引用了泰勒的书《拉威尔从学徒到工匠》

>

<?php namespace GQ\Routing;
class Redirector extends \Illuminate\Routing\Redirector {
    /**
     * ** Extended to add functionality for restoring POST input and the POST method after a login
     */
    public function guest($path, $status = 302, $headers = array(), $secure = null)
    {
        // Recording the method and input for the request so that it can be reloaded after being redirected back to the intended page
        $this->session->put('intended.method', $this->generator->getRequest()->getMethod());
        $this->session->put('intended.input', $this->generator->getRequest()->all());

        return parent::guest($path, $status, $headers, $secure);
    }

    /**
     * ** Extended to record in the session when we redirect to an intended page so method and input can be loaded on the next page
     */
    public function intended($default = '/', $status = 302, $headers = array(), $secure = null)
    {
        $redirect_response = parent::intended($default, $status, $headers, $secure);

        // Set the intended.load session variable so we know we returned to the intended page and can load the additional method and input
        return $redirect_response->with('intended.load', true);
    }
}
?>

创建一个新的服务提供程序,在IOC容器中通过“重定向”进行写操作。我最初尝试扩展RoutingServiceProvider,但在工作中遇到了问题。

<?php namespace App\Providers;

use GQ\Routing\Redirector;
use Illuminate\Support\ServiceProvider;
class RedirectServiceProvider extends ServiceProvider {

    protected $defer = true;

    /**
     * Register the Redirector service.
     *
     * ** Copy of class registerRedirector from RoutingServiceProvider,
     * using a different "use" statement at the top to use the extended Redirector class
     * Extending the RoutingServiceProvider was more of a pain to do right since it is loaded as a base provider in the Application
     *
     * @return void
     */
    public function register()
    {
        $this->app['redirect'] = $this->app->share(function($app)
        {
            $redirector = new Redirector($app['url']);

            // If the session is set on the application instance, we'll inject it into
            // the redirector instance. This allows the redirect responses to allow
            // for the quite convenient "with" methods that flash to the session.
            if (isset($app['session.store']))
            {
                $redirector->setSession($app['session.store']);
            }

            return $redirector;
        });
    }
    public function provides() {
        return array('redirect');
    }
}

创建一个新的服务提供者,它将在重定向后设置预期的方法和输入。

<?php

namespace GQ\Providers;

use Illuminate\Support\ServiceProvider;

class IntendedUrlServiceProvider extends ServiceProvider {
    /**
     * Bootstrap the application events.
     *
     * @return void
     */
    public function boot() {
        // Check to see if we were redirected to this page with the Redirect::intended().
        //        We extended the class to track when the redirect occurs so we know to reload additional request data
        if (\Session::has('intended.load')) {
            // intended.load could be set without these being set if we were redirected to the default page
            //        if either exists, both should exist but checking separately to be safe
            if (\Session::has('intended.method')) {
                \Request::setMethod(\Session::get('intended.method'));
            }
            if (\Session::has('intended.input')) {
                \Request::replace(\Session::get('intended.input'));
            }
            // Erase all session keys created to track the intended request
            \Session::forget('intended');
        }
    }

    public function register() {
    }
}

最后,在app/config/app中将2个新的服务提供商添加到提供商阵列中。php

'GQ\Providers\RedirectServiceProvider',
'GQ\Providers\IntendedUrlServiceProvider',

希望这能引导你走向一个好的方向。这对我很有效,但我还没有广泛测试过。也许如果它继续工作得很好,我们可以构建一个作曲家包或获得Laravel中包含的能力。

 类似资料:
  • 我有一个网页,这是一个邮政路线。这个页面有一个删除按钮,可以路由到另一个POST路由,在这里我删除指定的数据库行并重定向回第一个页面。 问题是,当我使用任何back()或reway()函数时,它们似乎会产生对上一个URL的GET请求。但上一页是仅限POST页。 如何将POST请求和POST数据重定向回?

  • 是否可以将用户重定向到Laravel中的POST路由。我有两张表格。表格一发送到包含表格二的路线,表格二发送到最终路线,然后进行验证。如果

  • 所以我正在尝试为内部项目开发一个rest API,我遇到了一个问题,当表单请求验证失败时,它会显示@index响应。 所以我有两条路线; 列出所有客户端,创建一个新客户端,我在方法上获得了一个表单请求验证器,该验证器检查为客户端提供的名称。 我想要的是,当验证器失败时,它会显示带有验证错误的JSON响应。但我认为,验证失败了,所以它重定向回同一个页面,但重定向是GET,而不是POST,因此它列出了

  • 我正在使用Spring Integration Filter对传入消息强制执行一些验证逻辑。验证的结果需要发回消息网关调用方,以便通知请求的具体错误。 null 配置 网关 过滤器

  • 这似乎是一个非常基本的流程,而且Laravel有很多很好的基本解决方案,我觉得我错过了一些东西。 用户单击需要身份验证的链接。Laravel的身份验证过滤器启动并将它们路由到登录页面。用户登录,然后转到他们试图在“身份验证”过滤器启动之前进入的原始页面。 有没有一个好方法可以知道他们最初想要到达的页面?由于Laravel是拦截请求的人,我不知道它是否会在用户登录后跟踪某个地方以方便路由。 如果没有

  • 我正在对我的Laravel控制器进行简单验证: 我的问题是,如果失败,这个验证会将我重定向到主,我通过AJAX发出请求,我知道Laravel会检测到通过Ajax发出的请求,但它只有在正常请求(我发送的典型请求标题与内容类型应用程序/json和正文中我发送了一个正常的JSON 但是Laravel无法检测到当te Ajax请求不是时,我使用的是JavaScript的对象,因此,我没有发送标题,而是在正