Back

How to handle CORS?


I have two domains: domain.dev and api.domain.dev.

I want to be able to do a ajax (POST, GET) call from domain.com to api.domain.dev.

In my route if I do this

$headers = [
    'Access-Control-Allow-Origin'      => 'http://domain.dev',
];

return Response::json( $validator->messages(), 400, $headers);

Everything works.

I want to be able to create a filter named cors that places that header into the routes I decide, like so:

Route::filter('cors', function($route, $request, $response)
{
    $response->headers->set('Access-Control-Allow-Origin', 'http://domain.dev');
    return $response;
});

And in my route I add that filter like so:

Route::group(array(
    'domain' => 'api.domain.dev',
    'as' => 'api.accommodation.check_availibility',
    'after' => 'cors'
), function()
{

    Route::post('/accommodation/check_availibility',function()
    {
        return Response::json( $validator->messages(), 400);
    });

});

But then it stops working. Any help?

jamesflight replied 3 years ago Solution

I normally just use Laravel Cors for this.

It allows you to set up different cors settings for different paths in a configuration file.

mabasic replied 3 years ago

jamesflight said:

I normally just use Laravel Cors for this.

It allows you to set up different cors settings for different paths in a configuration file.

Yeah, I gave up on doing this this way, because it does not work and I have spend too much time trying to figure it.

laravel-cors solved my problem.

muuknl replied 3 years ago

Can you show me your laravel-cors configuration, because it still doesn't work for me.

barryvdh replied 3 years ago

Please create an issue on Github if it doesn't work.

rishabhp replied 5 months ago

I am using Laravel 5.4 and didn't want to use a package so ended up writing my own middleware. The code looks like this:

<?php
 
namespace App\Http\Middleware;
 
use Closure;
 
class Cors
{
    private static $allowedOriginsWhitelist = [
      'http://localhost:8000'
    ];
 
    // All the headers must be a string
 
    private static $allowedOrigin = '*';
 
    private static $allowedMethods = 'OPTIONS, GET, POST, PUT, PATCH, DELETE';
 
    private static $allowCredentials = 'true';
 
    private static $allowedHeaders = '';
 
    /**
     * Handle an incoming request.
     *
     * @param  \Illuminate\Http\Request  $request
     * @param  \Closure  $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {
      if (! $this->isCorsRequest($request))
      {
        return $next($request);
      }
 
      static::$allowedOrigin = $this->resolveAllowedOrigin($request);
 
      static::$allowedHeaders = $this->resolveAllowedHeaders($request);
 
      $headers = [
        'Access-Control-Allow-Origin'       => static::$allowedOrigin,
        'Access-Control-Allow-Methods'      => static::$allowedMethods,
        'Access-Control-Allow-Headers'      => static::$allowedHeaders,
        'Access-Control-Allow-Credentials'  => static::$allowCredentials,
      ];
 
      // For preflighted requests
      if ($request->getMethod() === 'OPTIONS')
      {
        return response('', 200)->withHeaders($headers);
      }
 
      $response = $next($request)->withHeaders($headers);
 
      return $response;
    }
 
    /**
     * Incoming request is a CORS request if the Origin
     * header is set and Origin !== Host
     *
     * @param  \Illuminate\Http\Request  $request
     */
    private function isCorsRequest($request)
    {
      $requestHasOrigin = $request->headers->has('Origin');
 
      if ($requestHasOrigin)
      {
        $origin = $request->headers->get('Origin');
 
        $host = $request->getSchemeAndHttpHost();
 
        if ($origin !== $host)
        {
          return true;
        }
      }
 
      return false;
    }
 
    /**
     * Dynamic resolution of allowed origin since we can't
     * pass multiple domains to the header. The appropriate
     * domain is set in the Access-Control-Allow-Origin header
     * only if it is present in the whitelist.
     *
     * @param  \Illuminate\Http\Request  $request
     */
    private function resolveAllowedOrigin($request)
    {
      $allowedOrigin = static::$allowedOrigin;
 
      // If origin is in our $allowedOriginsWhitelist
      // then we send that in Access-Control-Allow-Origin
 
      $origin = $request->headers->get('Origin');
 
      if (in_array($origin, static::$allowedOriginsWhitelist))
      {
        $allowedOrigin = $origin;
      }
 
      return $allowedOrigin;
    }
 
    /**
     * Take the incoming client request headers
     * and return. Will be used to pass in Access-Control-Allow-Headers
     *
     * @param  \Illuminate\Http\Request  $request
     */
    private function resolveAllowedHeaders($request)
    {
      $allowedHeaders = $request->headers->get('Access-Control-Request-Headers');
 
      return $allowedHeaders;
    }
}

Then put this middleware in app/Http/Kernel.php:

protected $middleware = [
    // Other middleware classes ...
    \App\Http\Middleware\Cors::class,
];

Also written an article on this.

phpScots replied 1 week ago

For handing Cross-origin resource sharing (CORS) in Laravel 5.5 you can visit http://www.laravelinterviewquestions.com/2017/12/cross-origin-request-blocked-error-laravel.html


Sign in to participate in this thread!



We'd like to thank these amazing companies for supporting us