Webhooks

Overview

The purpose of webhooks are to provide more realtime updates versus performing query requests. Currently webhooks can be triggered as transactions, settlements, and invoices are processed within the gateway platform.

How to Enable

Webhooks can be created within the Virtual Terminal as a Gateway Admin under "Developer Hub" -> "Webhooks" -> "Create New +"

NOTE: You can create up to a maximum of 5 webhooks for each type (Transaction, Settlement and Invoice)

Security

Webhook post requests are sent with a header "Signature" that is HMAC SHA 256 signed and then base64 url encoded. To verify webhook post signatures, retrieve "Signature" from header. Base64 url decode and use HMAC SHA 256 to check using your signature UUID located in the control panel under the webhook previously created.

C#

using Newtonsoft.Json; 
using System;
using System.Security.Cryptography;
using System.Text;

public static class SignatureValidator
{
public static bool VerifySignature(SignedMessage message, string publicKey)
{
if (message.Resource == null)
{
throw new ArgumentNullException(nameof(message.Resource), "Resource field cannot be null");
}
string resourceJson = JsonConvert.SerializeObject(message.Resource);
byte[] dataBytes = Encoding.UTF8.GetBytes(resourceJson);
byte[] signatureBytes = Convert.FromBase64String(message.Signature);

using (SHA256 sha256 = SHA256.Create())
{
byte[] hashBytes = sha256.ComputeHash(dataBytes);
using (RSA rsa = RSA.Create())
{
// Note: Public key must be in PEM format
rsa.ImportFromPem(publicKey.ToCharArray());
return rsa.VerifyHash(hashBytes, signatureBytes, HashAlgorithmName.SHA256, RSASignaturePadding.Pkcs1);
}
}
}
}

Acknowledge and Retry

Webhook notifications are processed within a few seconds of a transaction, settlement, or invoice being created or updated. Webhooks need to be acknowledged with a 200 response, or the system will treat them as undelivered, and retry delivery using an exponential backoff strategy until retry maximum is reached.

Core Webhooks Model

public class SignedMessage 
{
public string ResourceType { get; }
public string SubType { get; }
public object Resource { get; }
public string TraceId { get; }
public DateTime ActionDateTime { get; }
public string HashAlg { get; }
public string SignatureAlg { get; }
public string Signature { get; }
}

Transaction Example

{ 
"resourceType": "TRANSACTION",
"subType": "Sale",
"resource":{
"transactionId": "<guid>",
"referencedTransactionId": "<guid>",
"invoiceId": "<guid>",
"type": "SALE",
"authorizationSubtype": "ESTIMATED",
"paymentMethod": "CARD",
"paymentType": "CARD",
"poNumber": "string",
"ipAddress": "string",
"description": "string",
"transactionSource": "Api",
"emailReceipt": true,
"emailAddress": "string",
"status": "PENDINGSETTLEMENT",
"payableBatchId": "<guid>",
"response": "string",
"responseCode": 0,
"authCode": "string",
"processorResponseCode": "string",
"processorResponseText": "string",
"processor": {
"processorId": "<guid>",
"name": "string",
"type": "string",
"merchantId": "string",
"groupId": "string",
"isVirtualTerminal": true,
"isCardPresent": true
},
"transactionRemit": {
"baseAmount": 0,
"amount": 0,
"amountAuthorized": 0,
"amountCaptured": 0,
"amountSettled": 0,
"amountRefunded": 0,
"taxAmount": 0,
"paymentAdjustmentType": 0,
"paymentAdjustmentValue": 0,
"tip": 0,
"cashBack": 0,
"taxExempt": true,
"shippingAmount": 0,
"surcharge": 0,
"discountAmount": 0,
"serviceFee": 0,
"nationalTaxAmount": 0,
"dutyAmount": 0,
"currencyCode": 0
},
"transactionAddresses": [
{
"transactionAddressId": "<guid>",
"isShipping": true,
"isBilling": true,
"firstName": "string",
"lastName": "string",
"company": "string",
"email": "string",
"phone": "string",
"fax": "string",
"addressLine1": "string",
"addressLine2": "string",
"city": "string",
"state": "string",
"postalCode": "string",
"country": "string"
}
],
"transactionPaymentMethod": {
"transactionPaymentMethodId": "<guid>",
"ach": {
"maskedAccount": "string",
"accountType": "Checking",
"secCode": "CCD",
"checkNum": 0
},
"card": {
"maskedCard": "string",
"cardType": "VISA",
"expirationDate": "string",
"token": "string",
"tenderType": "CREDIT",
"productSubType": "SNAP",
"emvTlvToken": "string",
"hasAssociatedCvv": true
},
"avsResponse": "string",
"cvvResponse": "string",
"cardHolderName": "string",
"cardEntryType": 0
},
"customer": {
"customerId": "<guid>",
"name": "string"
},
"createdDateTime": "2024-02-06T13:33:24.051Z",
"modifiedDateTime": "2024-02-06T13:33:24.051Z",
"capturedDateTime": "2024-02-06T13:33:24.051Z",
"settledDateTime": "2024-02-06T13:33:24.051Z",
"settlementId": "<guid>",
"timeZone": "string",
"systemTraceAuditNumber": "string",
"terminal": {
"terminalId": "<guid>",
"sourceTerminalId": "string",
"sourceDatawireId": "string"
},
"createdByUser": {
"gatewayUserId": "<guid>",
"firstName": "string",
"lastName": "string"
},
"gateway": {
"gatewayId": "<guid>",
"name": "string",
"categoryCode": "string"
},
"customFieldEntries": [
{
"customFieldId": 0,
"name": "string",
"value": "string",
"modifiedByUserId": "<guid>",
"modifiedDateTime": "2024-02-06T13:33:24.051Z",
"type": "string",
"customFieldCategoryName": "string",
"customFieldCategoryId": 0,
"dataType": "string"
}
],
"features": [
{
"code": "string",
"displayName": "string"
}
]
},
"traceId": "string",
"actionDateTime": "2024-02-06T13:33:24.051Z",
"hashAlg": "SHA256",
"signatureAlg": "RSA",
"signature": "string"
}

Settlement Example

{ 
"resourceType": "TRANSACTION",
"subType": "Sale",
"resource":{
"settlementId": "<guid>",
"gatewayId": "<guid>",
"processorId": "<guid>",
"processorName": "<string>",
"batchDate": "<ISO8601>",
"transactionsCount": 0,
"capturedAmount": 0,
"creditAmount": 0,
"surchargeAmount": 0,
"paymentAdjustmentAmount": 0,
"baseAmount": 0,
"netAmount": 0,
"netDepositAmount": 0,
"responseCode": 0,
"responseMessage": "<string>",
"sourceLastActionAt": "<ISO8601>"
}
],
"acceptedSettlementsStats": {
"transactionsCount": 0,
"capturedAmount": 0,
"creditAmount": 0,
"surchargeAmount": 0,
"paymentAdjustmentAmount": 0,
"baseAmount": 0,
"netAmount": 0,
"netDepositAmount": 0
},
"offset": 0,
"limit": 0,
"rowCount": 0,
"sortColumn": "<string>",
"sortDirection": "<string>"
},
"traceId": "string",
"actionDateTime": "2024-02-06T13:33:24.051Z",
"hashAlg": "SHA256",
"signatureAlg": "RSA",
"signature": "string"
}
}

Invoice Example

{ 
"resourceType": "INVOICE",
"subType": "",
"resource" {
"invoiceId": "<guid>",
"title": "string",
"number": "string",
"invoiceStatus": {
"invoiceStatusId": 0,
"name": "string"
},
"invoiceType": {
"invoiceTypeId": 0,
"name": "string"
},
"amountCaptured": 0,
"remainingBalance": 0,
"subtotal": 0,
"shipping": 0,
"total": 0,
"tax": 0,
"fees": 0,
"discounts": 0,
"requireShippingInfo": true,
"requireBillingInfo": true,
"invoiceDate": "string",
"dueDate": "string",
"message": "string",
"createdByUserId": "<guid>",
"createdDateTime": "string",
"modifiedByUserId": "<guid>",
"modifiedDateTime": "string",
"revisionNumber": 0,
"gateway": {
"gatewayId": "<guid>",
"name": "string",
"timezone": "string"
},
"customer": {
"customerId": "<guid>",
"name": "string"
},
"invoicePaymentMethod": {
"invoicePaymentMethodId": "<guid>",
"cardProcessorId": "<guid>",
"achProcessorId": "<guid>",
"secCode": 0,
"card": true,
"ach": true
},
"lineItems": [
{
"lineItemId": "<guid>",
"name": "string",
"description": "string",
"quantity": 0,
"unitPrice": 0,
"discount": 0,
"shippedAmount": 0,
"freightAmount": 0,
"unitOfMeasure": {
"unitOfMeasureId": 0,
"name": "string"
},
"isTaxable": true,
"localTaxPercent": 0,
"nationalTaxPercent": 0
}
],
"invoiceAddresses": [
{
"invoiceAddressId": "<guid>",
"addressId": "<guid>",
"isShipping": true,
"isBilling": true,
"isRemittance": true,
"firstName": "string",
"lastName": "string",
"company": "string",
"email": "string",
"phone": "string",
"fax": "string",
"addressLine1": "string",
"addressLine2": "string",
"city": "string",
"state": "string",
"postalCode": "string",
"country": "string"
}
],
"invoiceNotifications": [
{
"invoiceNotificationGroupId": "<guid>",
"notificationMethod": {
"invoiceNotificationMethodId": 0,
"name": "string"
},
"notificationStatus": {
"invoiceNotificationStatusId": 0,
"name": "string"
},
"notificationEventType": {
"invoiceNotificationEventTypeId": 0,
"name": "string"
},
"mainRecipient": "string",
"cc": [
"string"
],
"bcc": [
"string"
],
"deliveryDateTime": "string"
}
],
"transactions": [
{
"transactionId": "<guid>",
"transactionType": 0,
"paymentType": 0,
"status": 0,
"remit": {
"settledAmount": 0,
"capturedAmount": 0,
"baseAmount": 0,
"authorizedAmount": 0,
"taxAmount": 0,
"surchargeAmount": 0,
"paymentAdjustmentAmount": 0,
"paymentAdjustmentType": 0,
"ach": {
"maskedAccount": "string",
"accountType": 0
},
"card": {
"maskedCard": "string",
"cardType": 0
},
"settledDateTime": "string"
},
"createdDateTime": "string"
}
],
"customFieldEntries": [
{
"customFieldId": 0,
"name": "string",
"value": "string",
"modifiedByUserId": "<guid>",
"modifiedDateTime": "<datetime>",
"type": "string",
"customFieldCategoryName": "string",
"customFieldCategoryId": 0,
"dataType": "string"
}
]
},
"traceId": "string",
"actionDateTime": "2024-02-06T13:33:24.051Z",
"hashAlg": "SHA256",
"signatureAlg": "RSA",
"signature": "string"
}
}