Sign In

Cancel Transaction

Cancel a payment that has not been processed yet.

POST/v1/route/transaction-cancel

Cancels the most recent transaction for a merchant_transaction_id, but only while it is still in the INITIATED state. Once a payment has succeeded, failed or dropped it can no longer be cancelled.

Authentication

This endpoint is authenticated with your API key plus a per-request SHA-256 hash. Send the key in X-API-Key and the hash in Hash:

Hash formula

Hash = SHA256(key|merchant_transaction_id|salt), joined with the | character. Your salt is a server-side secret — see the Authentication guide.

Headers

HeaderTypeRequiredDescription
X-API-KeystringRequiredYour merchant API key.
HashstringRequiredSHA-256 auth hash (see Authentication).
Content-TypestringRequiredMust be application/json.

Request Parameters

ParameterTypeRequiredDescription
merchant_transaction_idstringRequiredThe reference of the payment to cancel.
Non-empty string.

Responses

A successful call returns HTTP 200 OK. Response fields:

FieldTypeDescription
successbooleantrue when cancelled.
messagestringHuman-readable result.

Example responses

Success
200 OK
{
    "success": true,
    "message": "Transaction cancelled"
}
Already processed
400 Bad Request
{
    "success": false,
    "message": "Transaction cannot be cancelled as it is already processed"
}
Not found
404 Not Found
{
    "success": false,
    "message": "Transaction not found"
}

Status Codes

StatusMeaning
200 OKTransaction cancelled.
400 Bad RequestMissing reference, or transaction not in a cancellable state.
404 Not FoundNo transaction matches the reference.

Error Codes

StatusMessageReason
400Transaction cannot be cancelled as it is already processedStatus is not INITIATED.
404Transaction not foundNo transaction for that reference.

Validation Rules

  • merchant_transaction_id — required, non-empty after trimming.
  • Only transactions currently in INITIATED status can be cancelled.

Notes

  • Only the most recent transaction (by creation time) for the reference is affected.
  • Cancellation is irreversible — the transaction moves to CANCELLED and can no longer be paid.

Best Practices

  • Check Transaction Status before cancelling to confirm the payment is still INITIATED.
Request · POST
# 1. Compute the auth hash: sha256(key|merchant_transaction_id|salt)
API_KEY="YOUR_API_KEY"
API_SALT="YOUR_API_SALT"
HASH=$(printf '%s' "$API_KEY|ORDER-2026-0001|$API_SALT" | openssl dgst -sha256 | awk '{print $2}')

# 2. Call the API
curl -X POST "https://api.growthbnk.com/v1/route/transaction-cancel" \
  -H "Content-Type: application/json" \
  -H "X-API-Key: $API_KEY" \
  -H "Hash: $HASH" \
  -d '{
    "merchant_transaction_id": "ORDER-2026-0001"
}'
import hashlib
import requests

API_KEY = "YOUR_API_KEY"
API_SALT = "YOUR_API_SALT"
BASE_URL = "https://api.growthbnk.com"

payload = {
    'merchant_transaction_id': 'ORDER-2026-0001'
}

# Auth hash: sha256(key|merchant_transaction_id|salt)
signing = f"{API_KEY}|ORDER-2026-0001|{API_SALT}"
auth_hash = hashlib.sha256(signing.encode("utf-8")).hexdigest()

response = requests.post(
    f"{BASE_URL}/v1/route/transaction-cancel",
    json=payload,
    headers={
        "Content-Type": "application/json",
        "X-API-Key": API_KEY,
        "Hash": auth_hash,
    },
    timeout=30,
)
response.raise_for_status()
print(response.json())
<?php
$apiKey  = 'YOUR_API_KEY';
$apiSalt = 'YOUR_API_SALT';
$baseUrl = 'https://api.growthbnk.com';

$payload = [
    'merchant_transaction_id' => 'ORDER-2026-0001'
];

// Auth hash: sha256(key|merchant_transaction_id|salt)
$signing = "{$apiKey}|ORDER-2026-0001|{$apiSalt}";
$authHash = hash('sha256', $signing);

$ch = curl_init("{$baseUrl}/v1/route/transaction-cancel");
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'POST',
    CURLOPT_HTTPHEADER     => [
        'Content-Type: application/json',
        "X-API-Key: {$apiKey}",
        "Hash: {$authHash}",
    ],
    CURLOPT_POSTFIELDS => json_encode($payload),
]);
$response = curl_exec($ch);
curl_close($ch);
echo $response;
const crypto = require('crypto');

const API_KEY = 'YOUR_API_KEY';
const API_SALT = 'YOUR_API_SALT';
const BASE_URL = 'https://api.growthbnk.com';

const payload = {
    'merchant_transaction_id': 'ORDER-2026-0001'
};

// Auth hash: sha256(key|merchant_transaction_id|salt)
const signing = `${API_KEY}|ORDER-2026-0001|${API_SALT}`;
const authHash = crypto.createHash('sha256').update(signing).digest('hex');

const response = await fetch(`${BASE_URL}/v1/route/transaction-cancel`, {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
    'X-API-Key': API_KEY,
    'Hash': authHash,
  },
  body: JSON.stringify(payload),
});
console.log(await response.json());
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;

public class GrowthBnkExample {
    public static void main(String[] args) throws Exception {
        String apiKey = "YOUR_API_KEY";
        String apiSalt = "YOUR_API_SALT";
        String baseUrl = "https://api.growthbnk.com";

        String payload = """
{
    "merchant_transaction_id": "ORDER-2026-0001"
}
""";

        // Auth hash: sha256(key|merchant_transaction_id|salt)
        String signing = apiKey + "|ORDER-2026-0001|" + apiSalt;
        String authHash = sha256Hex(signing);

        HttpRequest request = HttpRequest.newBuilder()
            .uri(URI.create(baseUrl + "/v1/route/transaction-cancel"))
            .header("Content-Type", "application/json")
            .header("X-API-Key", apiKey)
            .header("Hash", authHash)
            .method("POST", HttpRequest.BodyPublishers.ofString(payload))
            .build();

        HttpResponse<String> response = HttpClient.newHttpClient()
            .send(request, HttpResponse.BodyHandlers.ofString());
        System.out.println(response.body());
    }

    private static String sha256Hex(String input) throws Exception {
        byte[] digest = MessageDigest.getInstance("SHA-256")
            .digest(input.getBytes(StandardCharsets.UTF_8));
        StringBuilder sb = new StringBuilder();
        for (byte b : digest) sb.append(String.format("%02x", b));
        return sb.toString();
    }
}
using System;
using System.Net.Http;
using System.Security.Cryptography;
using System.Text;
using System.Threading.Tasks;

class GrowthBnkExample
{
    static async Task Main()
    {
        var apiKey = "YOUR_API_KEY";
        var apiSalt = "YOUR_API_SALT";
        var baseUrl = "https://api.growthbnk.com";

        var payload = """
{
    "merchant_transaction_id": "ORDER-2026-0001"
}
""";

        // Auth hash: sha256(key|merchant_transaction_id|salt)
        var signing = $"{apiKey}|ORDER-2026-0001|{apiSalt}";
        var authHash = Convert.ToHexString(
            SHA256.HashData(Encoding.UTF8.GetBytes(signing))).ToLowerInvariant();

        using var client = new HttpClient();
        client.DefaultRequestHeaders.Add("X-API-Key", apiKey);
        client.DefaultRequestHeaders.Add("Hash", authHash);

        var content = new StringContent(payload, Encoding.UTF8, "application/json");
        var response = await client.PostAsync($"{baseUrl}/v1/route/transaction-cancel", content);
        Console.WriteLine(await response.Content.ReadAsStringAsync());
    }
}
package main

import (
	"bytes"
	"crypto/sha256"
	"encoding/hex"
	"fmt"
	"io"
	"net/http"
)

func main() {
	apiKey := "YOUR_API_KEY"
	apiSalt := "YOUR_API_SALT"
	baseURL := "https://api.growthbnk.com"

	payload := []byte(`{
    "merchant_transaction_id": "ORDER-2026-0001"
}`)

	// Auth hash: sha256(key|merchant_transaction_id|salt)
	signing := apiKey + "|ORDER-2026-0001|" + apiSalt
	sum := sha256.Sum256([]byte(signing))
	authHash := hex.EncodeToString(sum[:])

	req, _ := http.NewRequest("POST", baseURL+"/v1/route/transaction-cancel", bytes.NewReader(payload))
	req.Header.Set("Content-Type", "application/json")
	req.Header.Set("X-API-Key", apiKey)
	req.Header.Set("Hash", authHash)

	resp, err := http.DefaultClient.Do(req)
	if err != nil {
		panic(err)
	}
	defer resp.Body.Close()
	body, _ := io.ReadAll(resp.Body)
	fmt.Println(string(body))
}
require 'digest'
require 'json'
require 'net/http'
require 'uri'

api_key = 'YOUR_API_KEY'
api_salt = 'YOUR_API_SALT'
base_url = 'https://api.growthbnk.com'

payload = {
    'merchant_transaction_id' => 'ORDER-2026-0001'
}

# Auth hash: sha256(key|merchant_transaction_id|salt)
signing = "#{api_key}|ORDER-2026-0001|#{api_salt}"
auth_hash = Digest::SHA256.hexdigest(signing)

uri = URI("#{base_url}/v1/route/transaction-cancel")
http = Net::HTTP.new(uri.host, uri.port)
http.use_ssl = true

request = Net::HTTP::Post.new(uri, {
  'Content-Type' => 'application/json',
  'X-API-Key' => api_key,
  'Hash' => auth_hash
})
request.body = payload.to_json

response = http.request(request)
puts response.body
Request body
{
    "merchant_transaction_id": "ORDER-2026-0001"
}
Response
200 OK
{
    "success": true,
    "message": "Transaction cancelled"
}