2

I am working with Azure Function Apps to receive webhooks from Xero for processing. However, I am getting stuck with my HASH not being computed correctly.

I think it something to do with the way Python is processing the Body Request.

Here is the code:

#import Logging module to log errors to console
import logging

#import Azure Functions
import azure.functions as func

#import Cryptopackages
import hmac
import hashlib
import base64

#import JSON
import json

XERO_KEY = 'key here'

#function to generate key
def create_sha256_signature(key, message):
    messagecoded = bytes(message, 'UTF-8')
    return base64.b64encode(hmac.new(key.encode(), messagecoded, digestmod=hashlib.sha256).digest()).decode()

#Define Main function - Recieve a HTTP reponse
def main(req: func.HttpRequest) -> func.HttpResponse:
    logging.info('Recieved a Request from Xero')
    
    #Parse HASH Key from Header
    xerosign = req.headers.get('x-xero-signature')
    logging.info(xerosign)
    
    #Get JSON body
    Data = req.get_body()
    Body = Data
    #Body = json.dumps(payload, separators=(",", ":")).strip()
    logging.info(Body)
    
    #Get Signature from defined function
    signature = create_sha256_signature(XERO_KEY, str(Body))
    
    logging.info(signature)
    logging.info(xerosign)

    if hmac.compare_digest(xerosign, signature):
        return func.HttpResponse(
            status_code=200)
    else:
        return func.HttpResponse(
            status_code=401
            )

Body Request is

{
    "events": [],
    "lastEventSequence": 0,
    "firstEventSequence": 0,
    "entropy": "TXHKKDMKUHWFBYTVJSQU"
}

Header x-xero-signature = C7G5M2SVxs/fAJM8fFLahzex32Rr7jwMHixX/OgvkFQ=

2 Answers2

1

after reviewing what Rett Behrens put through and some more digging into the way the Azure Function App handles data. I have a working solution leveraging Node.js, it terms out the way Microsoft handles an API response, if you don't put in "body":"" it automatically responses with the body from the initial post request. Hence causing the problem where Xero excepts an empty body.

https://github.com/mast3rbow/Xero-Functionapp

The github repo includes my working examlpe and will enable a business to send Xero Events directly to Microsoft Power Automate to do some logic handling there.

0

I've published an example of implementing webhooks using node. While the language is different the concepts remain the same. It's important that you not modify the incoming raw request body, otherwise the signature verification will fail. When working with node and express this meant configuring the body-parser middleware to use the raw request body specifically for the webhooks endpoint. There is an example of that included in the linked article.

Additionally, another Xero Developer Evangelist wrote this post on implementing webhooks in aws lambda using python. While there is more in this article than you need, it does include a code snippet that should help you pass the "intent to receive" signature validation.

Rett Behrens
  • 181
  • 1