Skip to content

Instantly share code, notes, and snippets.

@paulredmond
Created April 24, 2017 21:55
Show Gist options
  • Save paulredmond/14523d3bd8062f9ce48cdd1340b3f171 to your computer and use it in GitHub Desktop.
Save paulredmond/14523d3bd8062f9ce48cdd1340b3f171 to your computer and use it in GitHub Desktop.
Laravel Middleware to Validate a signed Mailgun webhook
<?php
namespace App\Http\Middleware;
use Closure;
use Illuminate\Http\Response;
/**
* Validate Mailgun Webhooks
* @see https://documentation.mailgun.com/user_manual.html#securing-webhooks
*/
class ValidateMailgunWebhook
{
/**
* Handle an incoming request.
*
* @param \Illuminate\Http\Request $request
* @param \Closure $next
* @return mixed
*/
public function handle($request, Closure $next)
{
if (!$request->isMethod('post')) {
abort(Response::HTTP_FORBIDDEN, 'Only POST requests are allowed.');
}
if ($this->verify($request)) {
return $next($request);
}
abort(Response::HTTP_FORBIDDEN);
}
/**
* Build the signature from POST data
*
* @see https://documentation.mailgun.com/user_manual.html#securing-webhooks
* @param $request The request object
* @return string
*/
private function buildSignature($request)
{
return hash_hmac(
'sha256',
sprintf('%s%s', $request->input('timestamp'), $request->input('token')),
config('services.mailgun.secret')
);
}
private function verify($request)
{
// Check if the timestamp is fresh
if (abs(time() - $request->input('timestamp')) > 15) {
return false;
}
return $this->buildSignature($request) === $request->input('signature');
}
}
@danielcharrua
Copy link

danielcharrua commented Jul 20, 2018

Hello Paul, I was using this middleware for validating the "legacy webhooks" but this seems not to work with the new webhooks.
It needs a few tweaks, for example in line 45 $request->input('timestamp') needs to change to $request->input('signature.timestamp') and $request->input('token') to $request->input('signature.token').
The same in line 53 and 57, need to add signature.
Thank you.

@adibnoh
Copy link

adibnoh commented Oct 10, 2018

@danielcharrua your suggestion is working, thanks.

@tomredman
Copy link

Thanks for sharing this!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment