Documentation/JavaScript SDK
SERVER-SIDE JAVASCRIPT

PayCow
JavaScript SDK

A focused Node.js client for the payment endpoints already available in PayCow: create a hosted USDT payment, retrieve its status, and verify HMAC-SHA256 webhook signatures.

JS

@paycow/sdk

Downloadable CommonJS package with TypeScript declarations and no runtime dependencies.

NODE 18+TYPES INCLUDEDZERO DEPENDENCIES

Installation

Extract the downloaded archive and install the package from its local directory. The SDK uses the Fetch API and cryptography modules built into Node.js 18 and newer.

npm install ./paycow-javascript-sdk

Keep both credentials on your server. Browser bundles must never contain the API secret.

PAYCOW_API_KEY=your_api_key
PAYCOW_API_SECRET=your_api_secret
PAYCOW_WEBHOOK_SECRET=whsec_your_signing_secret

Create a payment

createPayment calls POST /api/payment/create. The customer or order identifier is sent as userId. The optional idempotency key is sent in both the request header and body, matching the backend replay guard.

const { PayCowClient } = require('@paycow/sdk');

const paycow = new PayCowClient({
  apiKey: process.env.PAYCOW_API_KEY,
  apiSecret: process.env.PAYCOW_API_SECRET
});

const payment = await paycow.createPayment({
  userId: 'player-2048',
  amount: '50.00',
  network: 'TRC20',
  addressSerialNo: 'WAL-1002',
  idempotencyKey: 'topup-2048-001'
});

console.log(payment.sessionId);
console.log(payment.paymentUrl);
console.log(payment.payableAmount);
console.log(payment.depositAddress);
Use payableAmount as the exact amount shown to the customer. PayCow may allocate a unique micro-amount when active payments share the same destination and network.

Retrieve payment status

getPaymentStatus calls the authenticated GET /api/payment/status/:sessionId endpoint.

const payment = await paycow.getPaymentStatus('66ce30d74c0c51a48f2d2903');

if (payment.status === 'PAID') {
  await creditBalanceOnce(payment.userId, payment.paymentReference);
}

if (payment.status === 'CONFIRMING') {
  console.log(payment.confirmations);
}

The backend can return PENDING, DETECTED, CONFIRMING, PAID, EXPIRED, or REJECTED.

Verify webhooks

Verification requires the unparsed request body, PayCow-Timestamp, PayCow-Signature, and the webhook signing secret from the merchant dashboard.

const express = require('express');
const { verifyWebhook } = require('@paycow/sdk');

const app = express();

app.post('/webhooks/paycow', express.raw({ type: 'application/json' }), async (req, res) => {
  const event = verifyWebhook({
    rawBody: req.body,
    timestamp: req.get('PayCow-Timestamp'),
    signature: req.get('PayCow-Signature'),
    secret: process.env.PAYCOW_WEBHOOK_SECRET
  });

  if (event.type === 'payment.paid') {
    await creditBalanceOnce(event.data.userId, event.data.paymentReference);
  }

  res.sendStatus(200);
});

The verifier checks the v1=<hex> signature with a timing-safe comparison and rejects timestamps outside the default 300-second window.

Error handling

HTTP failures raise PayCowApiError with the response status and parsed response body. Invalid local input raises PayCowValidationError.

const { PayCowApiError } = require('@paycow/sdk');

try {
  await paycow.getPaymentStatus(sessionId);
} catch (error) {
  if (error instanceof PayCowApiError) {
    console.error(error.statusCode, error.responseBody);
  }
  throw error;
}

API contract

SDK methodBackend endpointRequired values
createPaymentPOST /api/payment/createuserId, amount, network
getPaymentStatusGET /api/payment/status/:idsessionId
verifyWebhookLocal verificationRaw body, timestamp, signature, secret