Laravel-excel: No 'Access-Control-Allow-Origin' header is present on the requested resource

Created on 2 Apr 2019  路  5Comments  路  Source: Maatwebsite/Laravel-Excel

Hi, i'm actually using Laravel-Excel in a Lumen project and I am trying to export data in an excel file and download it as below:

My UsersExport:

use App\User;
use Maatwebsite\Excel\Concerns\FromCollection;

class UsersExport implements FromCollection
{
    /**
    * @return \Illuminate\Support\Collection
    */
    public function collection()
    {
        return User::all();
    }
}

My controller:

public function excel()
    {
        return Excel::download(new UsersExport(),'users.xlsx');
    } 

web.php:
$router->get('/download', 'CommunicationController@excel');

And when I'm trying to execute the excel() function i'm getting this error

image

However, I already created a CorsMiddleware.php and add it in my bootstrap/app.php long time ago and all the other functions works very well thanks of it.

app.php:

$app->middleware([
    App\Http\Middleware\CorsMiddleware::class
]);

CorsMiddleware.php:

<?php

namespace App\Http\Middleware;

use Closure;

class CorsMiddleware
{
    /**
     * Handle an incoming request.
     *
     * @param  \Illuminate\Http\Request  $request
     * @param  \Closure  $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {
        $headers = [
            'Access-Control-Allow-Origin'      => '*',
            'Access-Control-Allow-Methods'     => 'POST, GET, OPTIONS, PUT, DELETE',
            'Access-Control-Allow-Credentials' => 'true',
            'Access-Control-Max-Age'           => '86400',
            'Access-Control-Allow-Headers'     => 'Content-Type, Authorization, X-Requested-With, api_token'
        ];

        if ($request->isMethod('OPTIONS'))
        {
            return response()->json('{"method":"OPTIONS"}', 200, $headers);
        }

        $response = $next($request);
        foreach($headers as $key => $value)
        {
            $response->header($key, $value);
        }

        return $response;
    }
}

Did I forget something ? I'm stuck on it since yesterday and I really would like your help :'(

Here you can see the versions of Lumen I use and also maatwebsite/excel:

"require": {
        "php": ">=7.1.3",
        "guzzlehttp/guzzle": "^6.3",
        "laravel/lumen-framework": "5.7.*",
        "maatwebsite/excel": "^3.1",
        "phpoffice/phpspreadsheet": "^1.6",
        "vlucas/phpdotenv": "~2.2"
    },

Thank you!

Most helpful comment

Finally I found the solution, it was because of the CorsMiddleware file.

I changed to this:

$response = $next($request);

        $response->headers->set('Access-Control-Allow-Origin' , '*');
        $response->headers->set('Access-Control-Allow-Methods', 'POST, GET, OPTIONS, PUT, DELETE');
        $response->headers->set('Access-Control-Allow-Credentials', 'true');
        $response->headers->set('Access-Control-Max-Age', '86400');
        $response->headers->set('Access-Control-Allow-Headers', 'Content-Type, Accept, Authorization, X-Requested-With, Application');

        return $response;

Now I have no more problem with CORS.

Thanks anyway

All 5 comments

Prerequisites

  • [X] Able to reproduce the behaviour outside of your code, the problem is isolated to Laravel Excel.
  • [X] Checked that your issue isn't already filed.
  • [X] Checked if no PR was submitted that fixes this problem.

Versions

  • PHP version: 7.1.3
  • Laravel/lumen-framework version: 5.7
  • Package version: ^3.1

Description


As described upper, I'm trying to export data in an excel file and download it but I'm getting this error,
Access to fetch at 'http://localhost:8000/download' from origin 'http://localhost:3000' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource. If an opaque response serves your needs, set the request's mode to 'no-cors' to fetch the resource with CORS disabled.

Steps to Reproduce


run php artisan make:export UsersExport --model=User to get a UserExport.php file which looks like this:

<?php

namespace App\Exports;

use App\User;
use Maatwebsite\Excel\Concerns\FromCollection;

class UsersExport implements FromCollection
{
    /**
    * @return \Illuminate\Support\Collection
    */
    public function collection()
    {
        return User::all();
    }
}

and create this function in your the controller file:

public function excel()
    {
        return Excel::download(new UsersExport(),'users.xlsx');
    }

Then add in the middleware folder the CorsMiddleware file:
```

namespace App\Http\Middleware;

use Closure;

class CorsMiddleware
{
/*
* Handle an incoming request.
*
* @param \Illuminate\Http\Request $request
* @param \Closure $next
* @return mixed
*/
public function handle($request, Closure $next)
{
$headers = [
'Access-Control-Allow-Origin' => '
',
'Access-Control-Allow-Methods' => 'POST, GET, OPTIONS, PUT, DELETE',
'Access-Control-Allow-Credentials' => 'true',
'Access-Control-Max-Age' => '86400',
'Access-Control-Allow-Headers' => 'Content-Type, Authorization, X-Requested-With, api_token'
];

    if ($request->isMethod('OPTIONS'))
    {
        return response()->json('{"method":"OPTIONS"}', 200, $headers);
    }

    $response = $next($request);
    foreach($headers as $key => $value)
    {
        $response->header($key, $value);
    }

    return $response;
}

}

and add it to the ``bootstrp/app.php``:

$app->middleware([
App\Http\Middleware\CorsMiddleware::class
]);
```

Finnally add in route/web.php: $router->get('/download, 'CommunicationController@excel');

Expected behavior:


I expected an excel file to be downloaded

Actual behavior:


I'm getting this on the console of google chrome each time I click on the button that runs the download link
image
I just don't undertand why the CORS block this request and not the others. I also have other functions that works properly thanks to all I added on CorsMiddleware. Do I need to add other parameters ? I so on other similar issues that they had to add parameters but they were using old versions of laravel-excel.

Thank you for helping me

I do see in your error message that the port is different:
http://localhost:8000/download and http://localhost:3000

Exactly @GlennM,
it's because I'm using the Lumen project as an API that is running on port 8000 and a React Front-end which is running on port 3000
That's all

Finally I found the solution, it was because of the CorsMiddleware file.

I changed to this:

$response = $next($request);

        $response->headers->set('Access-Control-Allow-Origin' , '*');
        $response->headers->set('Access-Control-Allow-Methods', 'POST, GET, OPTIONS, PUT, DELETE');
        $response->headers->set('Access-Control-Allow-Credentials', 'true');
        $response->headers->set('Access-Control-Max-Age', '86400');
        $response->headers->set('Access-Control-Allow-Headers', 'Content-Type, Accept, Authorization, X-Requested-With, Application');

        return $response;

Now I have no more problem with CORS.

Thanks anyway

Glad to hear the issue has been resolved. Thank you for using Laravel Excel!

Was this page helpful?
0 / 5 - 0 ratings