npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@realkal/easy-pay

v1.2.4

Published

A TypeScript/JavaScript client to integrate payment services (Chapa, Telebirr, M-Pesa, CBE Birr) easily in web or Node.js applications. Supports inline payments, hosted payments, and automatic payment verification with retries.

Downloads

27

Readme

EasyPay

A TypeScript/JavaScript client to integrate payment services (Chapa, Telebirr, M-Pesa, CBE Birr) easily in web or Node.js applications. Supports inline payments, hosted payments, and automatic payment verification with retries.

Installation

npm install @realkal/easy-pay
# or
yarn add @realkal/easy-pay
pnpm add @realkal/easy-pay

Importing

import { easyPay } from "@realkal/easy-pay";

Client Configuration (easyPay)

| Option | Type | Required | Default | Description | | ---------------- | ---------- | -------- | ----------------------------------------------------------------------- | --------------------------------------------- | | publicKey | string | ✅ | - | Chapa public key | | secretKey | string | ❌ | - | Chapa secret key, required for Chapa payments and transaction verification | | paymentOptions | string[] | ❌ | ["telebirr", "cbebirr", "ebirr", "mpesa", "chapa"] | Allowed payment methods | | callbackUrl | string | ❌ | - | URL to receive server-side callback | | returnUrl | string | ❌ | - | URL to redirect after payment | | generateRefId | () => string | ❌ | Random nanoid(10) | Custom transaction reference generator | | onSuccess | (paymentInfo: any) => void | ❌ | () => {} | Callback after successful payment | | onFailure | (error: string) => void | ❌ | () => {} | Callback after failed payment | | maxRetry | number | ❌ | 3 | Max retries for pending payments | | retryDelay | number | ❌ | 3 | Delay between retries in seconds |

Payment Properties (CreatePaymentProps)

| Property | Type | Required | Description | | --------------- | ---------------------------------------------------------- | -------- | --------------------------------------------------------- | | mobile | string | ✅ | User phone number, validated per payment type | | paymentType | "telebirr" \| "cbebirr" \| "ebirr" \| "mpesa" \| "chapa" | ✅ | Payment method | | amount | number | ✅ | Payment amount (minimum 1) | | txRef | string | ❌ | Optional transaction reference, auto-generated if missing | | email | string | ❌ | Customer email | | first_name | string | ❌ | Customer first name | | last_name | string | ❌ | Customer last name | | customization | object | ❌ | Payment UI customization options | | meta | Record<string, any> | ❌ | Extra metadata attached to the payment |

Customization example:

customization: {
  logo?: string;
  title?: string;
  description?: string;
}

Meta example:

meta: {
  userId: "123",
  campaignId: "456",
  note: "Special instructions"
}

Usage Examples (Updated for EasyPayResponse)

1. Basic Chapa Payment

const easyPayClient = new easyPay({
  publicKey: "CHAPUBK-xxxxxxxx",
  secretKey: "CHASECK-xxxxxxxx",
});

const result = await easyPayClient.createPayment({
  mobile: "0900123456",
  amount: 500,
  paymentType: "chapa",
  first_name: "John",
  last_name: "Doe",
  email: "[email protected]",
});

if (result.success) {
  console.log("Payment initiated successfully:", result.data);
} else {
  console.error("Payment failed:", result.message);
}

2. Payment with Customization

const result = await easyPayClient.createPayment({
  mobile: "0700123456",
  amount: 300,
  paymentType: "mpesa",
  customization: {
    logo: "https://example.com/logo.png",
    title: "Donation",
    description: "Support our cause",
  },
});

if (result.success) {
  console.log("Payment initiated successfully:", result.data);
} else {
  console.error("Payment failed:", result.message);
}

3. Payment with Metadata

const result = await easyPayClient.createPayment({
  mobile: "0900123456",
  amount: 200,
  paymentType: "telebirr",
  meta: {
    campaignId: "CAMPAIGN123",
    userId: "USER456",
    notes: "Priority user",
  },
});

if (result.success) {
  console.log("Payment initiated successfully:", result.data);
} else {
  console.error("Payment failed:", result.message);
}

4. Payment with Custom txRef

const result = await easyPayClient.createPayment({
  mobile: "0900123456",
  amount: 1000,
  paymentType: "chapa",
  txRef: "CUSTOM_REF_123",
  meta: { orderId: "ORDER789" },
});

if (result.success) {
  console.log("Payment initiated successfully:", result.data);
} else {
  console.error("Payment failed:", result.message);
}

5. Full Example (All Options)

const easyPayClient = new easyPay({
  publicKey: "CHAPUBK-xxxxxxxx",
  secretKey: "CHASECK-xxxxxxxx",
  callbackUrl: "https://example.com/callback",
  returnUrl: "https://example.com/return",
  maxRetry: 5,
  retryDelay: 5,
  onSuccess: (paymentInfo) => console.log("Payment succeeded:", paymentInfo),
  onFailure: (error) => console.log("Payment failed:", error),
});

const paymentResult = await easyPayClient.createPayment({
  mobile: "0900123456",
  amount: 750,
  paymentType: "telebirr",
  first_name: "John",
  last_name: "Doe",
  email: "[email protected]",
  customization: {
    logo: "https://example.com/logo.png",
    title: "Charity Donation",
    description: "Support our campaign",
  },
  meta: {
    userId: "USER123",
    campaignId: "CAMPAIGN456",
    note: "VIP user",
  },
});

if (paymentResult.success) {
  console.log("Payment data:", paymentResult.data);
} else {
  console.error("Payment error:", paymentResult.message);
}

6. Verify Transaction Server-Side (New)

You can verify any Chapa transaction server-side using verifyTransaction with the secretKey.

const transactionResult = await easyPayClient.verifyTransaction("TX_REF_123");

if (transactionResult.success) {
  console.log("Transaction verified successfully:", transactionResult.data);
} else {
  console.error("Transaction verification failed:", transactionResult.message);
}

Payment Verification

const verification = await easyPayClient.verifyPayment("TX_REF_123", "chapa");

if (verification.success) {
  console.log("Payment verified successfully:", verification.data);
} else {
  console.error("Payment verification failed:", verification.message);
}
  • Automatically retries if the payment is pending.
  • Calls onSuccess or onFailure callbacks automatically.
  • Retry behavior is configurable via maxRetry and retryDelay.

Return Type (EasyPayResponse)

type EasyPayResponse = {
  success: boolean;
  message: string;
  data?: {
    checkoutUrl?: string; // For Chapa hosted
    txRef?: string;       // For mobile money
    amount?: string;
    status?: string;
    createdAt?: string;
  } | null;
};
  • Both createPayment, verifyPayment, and verifyTransaction now always return EasyPayResponse.
  • message is always a string.
  • data is either a populated object or null.

Notes

  • Supports multiple payment methods in the same configuration.
  • Chapa payments and transaction verification require secretKey; others do not.
  • Inline payments automatically verify transactions.
  • Hosted payments return a checkout_url.
  • Return types are fully type-safe and consistent.

License

MIT © Endekalu Zemenu