I couldn't find a way to do this with API Gateway. I validated within the LAMBDA using (Python).
High level overview : Calculate HMAC signature with GITHUB_SECRET then compare to the signature passed from Github.
You can obviously simplify, intentionally verbose for readability. There may be better ways, but I couldn't find one.
Make sure your Webhook is configured for application/json. Hopefully this helps someone else.
import logging
import json
import hmac
import hashlib
import re
from urllib.parse import unquote
logger = logging.getLogger(__name__)
logger.setLevel(logging.DEBUG)
GITHUB_SECRET = 'SECRET FROM GITHUB CONSOLE'
def lambda_handler(event, context):
logger.info("Lambda execution starting up...")
incoming_signature = re.sub(r'^sha1=', '', event['headers']['X-Hub-Signature'])
incoming_payload = unquote(re.sub(r'^payload=', '', event['body']))
calculated_signature = calculate_signature(GITHUB_SECRET, incoming_payload.encode('utf-8'))
if incoming_signature != calculated_signature:
logger.error('Unauthorized attempt')
return {
'statusCode': 403,
'body': json.dumps('Forbidden')
}
logger.info('Request successfully authorized')
# do stuff in Lambda
return {
'statusCode': 200,
'body': json.dumps(f'Work in progress')
}
def calculate_signature(github_signature, githhub_payload):
signature_bytes = bytes(github_signature, 'utf-8')
digest = hmac.new(key=signature_bytes, msg=githhub_payload, digestmod=hashlib.sha1)
signature = digest.hexdigest()
return signature