🪝
Webhooks
Setup powerful event-driven payment workflows in minutes
Helio Webhooks allow developers to listen to Helio payments events such as transactions, payments, invoices paid, subscriptions created, paused or cancelled events, and build powerful payment workflows.
Security: Webhooks are linked to your Helio account. Log in to the Helio dashboard to generate your API key. Each Webhook generates a `sharedSecret` used with the target API to authenticate the endpoints with a Bearer auth header.
For Pay Links (1-time payments) and Pay Streams (recurring payments), we provide 4 API endpoints each for creating, listing, getting Webhooks by ID, and deleting a Webhook. API specs are published below:
get
/v1/webhook/paylink/transaction
post
/v1/webhook/paylink/transaction
get
/v1/webhook/paylink/transaction/{webhookId}
delete
/v1/webhook/paylink/transaction/{webhookId}
get
/v1/webhook/stream/transaction
post
/v1/webhook/stream/transaction
get
/v1/webhook/stream/transaction/{webhookId}
delete
/v1/webhook/stream/transaction/{webhookId}
The following is a curl command that will register the Webhook for paylinkID: 636a74162e72d4ad24ac9ce9 on new transaction event. This will send a POST request to targetUrl: https://target-url.com/post-endpoint.
curl -X POST \
https://api.hel.io/v1/webhook/paylink/transaction?apiKey=<apiKey> \
-H 'Accept: application/json' \
-H 'Content-Type: application/json' \
-H 'Authorization: Bearer {apiSecret}' \
-H 'cache-control: no-cache' \
-d '
{
"paylinkId": "636a74162e72d4ad24ac9ce9",
"targetUrl": "https://target-url.com/post-endpoint",
"events": ["CREATED"]
}
'
The API key needs to be associated with the same account of the underlying Pay Link in order to register the Webhook.
The response of this request will look as follows:
{
"id": "636cf9c095aeedb263968ee9",
"paylink": "636a74162e72d4ad24ac9ce9",
"company": "6343e77d91c393456aa56462",
"targetUrl": "https://target-url.com/post-endpoint",
"events": [
"CREATED"
]
}
Upon payment on the Pay Link
636cf9c095aeedb263968ee9
the targetUrl will receive HTTP [POST] request with the following payload:
export class PaylinkEventPayload {
event: PaylinkEvents
transaction: string;
transactionObject: Transaction;
}
export class Transaction {
id: string;
quantity: number;
fee?: string;
createdAt: string;
paymentType: PaymentRequestType;
meta: Meta;
}
export class Meta {
id: string;
transactionSignature: string;
amount: bigint;
recipientPK: string;
senderPK: string;
customerDetails: {
email?: string;
discordUsername?: string;
twitterUsername?: string;
fullName?: string;
country?: string;
deliveryAddress?: string;
phoneNumber?: string;
street?: string;
streetNumber?: string;
city?: string;
areaCode?: string;
additionalJSON?: string;
};
productDetails: {
name?: string;
value?: string;
};
splitRevenue: boolean;
remainingAccounts: {
amount: string;
recipient: string;
}[];
totalAmount: string;
currency: {
id: string;
symbol: string;
name: string;
mintAddress: string;
coinMarketCapId: number;
decimals: number;
symbolPrefix?: string;
order: number;
};
}
export enum PaymentRequestType {
PAYLINK = 'PAYLINK',
PAYSTREAM = 'PAYSTREAM',
}
export enum PaylinkEvents {
CREATED = 'CREATED',
}
You can list all the hooks that are registered for a Pay Link with the following curl reuqest:
curl \
https://api.hel.io/v1/webhook/paylink/transaction?apiKey=Uus~N8ePqcG8jaYxFfGajGu3US.Y8XlicIZwEoUqT~YGy7A7qjE-o-QXDN1N7MwF&paylinkId=636501dad706741f1ad63770
-H 'Accept: application/json' \
-H 'Content-Type: application/json' \
-H 'Authorization: Bearer {apiSecret}' \
-H 'cache-control: no-cache'
This will return an array of all Webhooks that are registered for the Pay Link. In case the API key isn't associated with Pay Link, an unauthorised request will be thrown.
[
{
"id": "636a3838591b00789e778b79",
"paylink": "636501dad706741f1ad63779",
"company": "6343e77d91c393456aa56422",
"targetUrl": "https://targetUrl.com",
"events": [
"CREATED"
]
}
]
You can delete any Webhook ID by calling the delete endpoint:
curl -X DELETE \
https://api.hel.io/v1/webhook/paylink/transaction/636a75ee5a9078bb9803a681?apiKey=Uus~N8ePqcG8jaYxFfGajGu3US.Y8XlicIZwEoUqT~YGy7A7qjE-o-QXDN1N7MwF
-H 'Accept: application/json' \
-H 'Content-Type: application/json' \
-H 'Authorization: Bearer {apiSecret}' \
-H 'cache-control: no-cache'
To be clear, in this example,
636a75ee5a9078bb9803a681
is the ID of the Webhook.
The following is a curl command that will register the Webhook for streamId: 636a74162e72d4ad24ac9ce9 on new transaction event. This will send a POST request to targetUrl: https://target-url.com/post-endpoint.
curl -X POST \
https://api.hel.io/v1/webhook/stream/transaction?apiKey=<apiKey> \
-H 'Accept: application/json' \
-H 'Content-Type: application/json' \
-H 'Authorization: Bearer {apiSecret}' \
-H 'cache-control: no-cache' \
-d '
{
"streamId": "636a74162e72d4ad24ac9ce9",
"targetUrl": "https://target-url.com/post-endpoint",
"events": ["STARTED", "ENDED"]
}
'
The API key needs to be associated with the same account of the underlying Stream in order to register the Webhook.
In the following example we register a Webhook to follow two events: stream start, and stream end
The response of this request will look as follows:
{
"id": "636cf9c095aeedb263968ee9",
"stream": "636a74162e72d4ad24ac9ce9",
"company": "6343e77d91c393456aa56462",
"targetUrl": "https://target-url.com/post-endpoint",
"events": [
"STARTED",
"ENDED"
]
"sharedToken": "security token"
}
When starting a stream on id
636cf9c095aeedb263968ee9
the targetUrl will receive the HTTP [POST] request with the following payload StreamEventPayload
export class StreamEventPayload {
event: StreamTransactionEvent;
transaction: PaystreamTransaction;
}
export class PaystreamTxWithMeta {
meta: {
id: string;
transactionSignature: string;
amount: string;
recipientPK: string;
senderPK: string;
customerDetails: {
email?: string;
discordUsername?: string;
twitterUsername?: string;
fullName?: string;
country?: string;
deliveryAddress?: string;
phoneNumber?: string;
street?: string;
streetNumber?: string;
city?: string;
areaCode?: string;
additionalJSON?: string;
};
productDetails: {
name?: string;
value?: string;
};
splitRevenue: boolean;
remainingAccounts: {
amount: bigint;
recipient: string;
}[];
totalAmount: number;
};
withdrawals: {
paystreamTx: string;
amount: string;
fee?: string;
}[];
fee: string;
paystream: string;
id: string;
paymentAccount: string;
startedAt: {
timestamp: string;
transactionSignature: string;
};
createdAt: string;
canceledAt: {
timestamp: number;
transactionSignature: string;
} | null;
endedAt: string;
interval: number;
paymentType: PaymentRequestType;
active: boolean;
isHelioX?: boolean;
}
export enum PaymentRequestType {
PAYLINK = 'PAYLINK',
PAYSTREAM = 'PAYSTREAM',
}
export enum StreamTransactionEvent {
STARTED = 'STARTED',
ENDED = 'ENDED',
}
Important every POST request to targetUrl includes Authorization header with Bearer token, which is the sharedSecret. The API consumer can choose to authenticate their endpoint with the following token.
You can list all the hooks that are registered for a stream with the following curl reuqest:
curl \
https://api.hel.io/v1/webhook/stream/transaction?apiKey=Uus~N8ePqcG8jaYxFfGajGu3US.Y8XlicIZwEoUqT~YGy7A7qjE-o-QXDN1N7MwF&streamId=636501dad706741f1ad63770
-H 'Accept: application/json' \
-H 'Content-Type: application/json' \
-H 'Authorization: Bearer {apiSecret}' \
-H 'cache-control: no-cache'
This will return an array of all Webhooks that are registered for the stream. In case the API key isn't associated with stream, an unauthorised request error will be thrown.
[
{
"id": "636a3838591b00789e778b79",
"stream": "636501dad706741f1ad63779",
"company": "6343e77d91c393456aa56422",
"targetUrl": "https://targetUrl.com",
"events": [
"STARTED",
"ENDED"
]
}
]
You can delete any Webhook ID by calling the delete endpoint:
curl -X DELETE \
https://api.hel.io/v1/webhook/stream/transaction/636a75ee5a9078bb9803a681?apiKey=Uus~N8ePqcG8jaYxFfGajGu3US.Y8XlicIZwEoUqT~YGy7A7qjE-o-QXDN1N7MwF
-H 'Accept: application/json' \
-H 'Content-Type: application/json' \
-H 'Authorization: Bearer {apiSecret}' \
-H 'cache-control: no-cache'
To be clear, in this example,
636a75ee5a9078bb9803a681
is the ID of the Webhook.
Last modified 30d ago