Skip to content
This repository has been archived by the owner on Feb 16, 2023. It is now read-only.

Commit

Permalink
[2.x] Add event listener (#450)
Browse files Browse the repository at this point in the history
* Test with append/prepend middleware
* Add eventlistener
  • Loading branch information
barryvdh committed Apr 28, 2020
1 parent b50ffb7 commit 138be6e
Show file tree
Hide file tree
Showing 4 changed files with 91 additions and 4 deletions.
31 changes: 27 additions & 4 deletions src/HandleCors.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@

use Closure;
use Asm89\Stack\CorsService;
use Illuminate\Foundation\Http\Events\RequestHandled;
use Illuminate\Http\Request;
use Illuminate\Contracts\Container\Container;
use Symfony\Component\HttpFoundation\Response;
Expand All @@ -15,7 +16,7 @@ class HandleCors

/** @var \Illuminate\Contracts\Container\Container $container */
protected $container;

public function __construct(CorsService $cors, Container $container)
{
$this->cors = $cors;
Expand Down Expand Up @@ -45,16 +46,38 @@ public function handle($request, Closure $next)
return $response;
}

// Add the headers on the Request Handled event as fallback in case of exceptions
if (class_exists(RequestHandled::class) && $this->container->bound('events')) {
$this->container->make('events')->listen(RequestHandled::class, function (RequestHandled $event) {
$this->addHeaders($event->request, $event->response);
});
}

// Handle the request
$response = $next($request);

// For OPTIONS (but not Preflight) vary the Request-Method header
if ($request->getMethod() === 'OPTIONS') {
$this->cors->varyHeader($response, 'Access-Control-Request-Method');
}

// Add the CORS headers to the Response
return $this->cors->addActualRequestHeaders($response, $request);
return $this->addHeaders($request, $response);
}

/**
* Add the headers to the Response, if they don't exist yet.
*
* @param Request $request
* @param Response $response
* @return Response
*/
protected function addHeaders(Request $request, Response $response): Response
{
if (! $response->headers->has('Access-Control-Allow-Origin')) {
// Add the CORS headers to the Response
$response = $this->cors->addActualRequestHeaders($response, $request);
}

return $response;
}

/**
Expand Down
28 changes: 28 additions & 0 deletions tests/BrowserTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -141,6 +141,34 @@ public function testFetchWildcard()
$this->assertFalse(File::exists(__DIR__ .'/Browser/invalid.flag'));
}

public function testPushMiddleware()
{
$this->tweakApplication(function ($app) {
// Add the middleware
/** @var Kernel $kernel */
$kernel = $app->make(Kernel::class);
$kernel->pushMiddleware(new class {
public function handle($request, \Closure $next)
{
if ($request->is('protected')) {
return response()->json(['message' => 'Authorization Required'], 401);
}
return $next($request);
}
});
});

File::delete(__DIR__ .'/Browser/invalid.flag');

$this->browse(function ($browser) {
$browser->visit('js/middleware.html')
->waitForText('passes: 1')
->assertSee('passes: 1');
});

$this->assertFalse(File::exists(__DIR__ .'/Browser/invalid.flag'));
}

public function testFetchInvalid()
{
$this->tweakApplication(function ($app) {
Expand Down
18 changes: 18 additions & 0 deletions tests/js/middleware.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
<html>
<head>
<meta charset="utf-8">
<title>Mocha Tests</title>
<link rel="stylesheet" href="mocha.css" />
</head>
<body>
<div id="mocha"></div>
<script src="expect.js"></script>
<script src="mocha.js"></script>
<script>mocha.setup('bdd')</script>
<script src="test.middleware.js"></script>
<script>
mocha.checkLeaks();
mocha.run();
</script>
</body>
</html>
18 changes: 18 additions & 0 deletions tests/js/test.middleware.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
(function() {
var CORS_SERVER;

CORS_SERVER = 'localhost:9292';

describe('CORS-INVALID', function() {
return it('should allow access to invalid auth resource', function(done) {
return fetch(`http://${CORS_SERVER}/protected`, {
method: 'GET',
mode: 'cors'
}).then((response) => {
expect(response.status).to.eql(401);
return done();
})
});
});

}).call(this);

0 comments on commit 138be6e

Please sign in to comment.