How to integrate imsafu with TypeScript

imsafu is a payment processing service that allows you to create and query payments. This document will guide you through accessing the imsafu service.

Prerequisites

Before getting started, please make sure you have the following prerequisites:

  1. Node.js installed on your computer (> v18).
  2. A package manager installed (such as npm or yarn).

Install Dependencies

There are no fixed dependencies for accessing the imsafu service. Here, we provide some default dependency libraries that you can replace with any other libraries that have similar functionality.

Run the following command to install the dependencies:

npm install axios ulid ethers

Import Required Modules

In your TypeScript file, import the necessary modules from the installed dependencies. Add the following import statements at the top of your file:

import axios from "axios";
import { ulid } from "ulid";
import { utils } from "ethers";

Create Required Variables for imsafu

To connect to the imsafu test server, you can use the following variables. If you want to connect to the production server, you can join the waiting list hereopen in new window.

const options = {
  "url": "https://devnet.imsafu.com",
  "api": "https://allowpay-api-devnet.fly.dev/v1",
  "apiSecret": "your-api-secret",
  "receiver": "your-wallet-account",
  "merchantBrand": "imsafu demo",
  "merchantRedirectURL": "https://merchant.com/redirect"
};

Create a New Payment

First, we need to generate a 32-character hex string as the ID for the new order.

const newOrderID = utils.hexlify(Buffer.from(ulid().padEnd(32), "utf8"));

To create a new payment, we need to implement a createPayment method. This method takes the payment amount as a parameter and returns a Promise that resolves to a PaymentResponse object.

async function createPayment(amount: number): Promise<PaymentResponse> {
  const newOrderID = utils.hexlify(Buffer.from(ulid().padEnd(32), "utf8")); // Generate new OrderID

  const payload = {
    payment: {
      orderID: newOrderID,
      receiver: options.receiver,
      amount: amount.toString(),
    },
    notifyURL: `${options.url}/notify`,
  };

  const res = await axios.post(`${options.api}/depositPay`, payload, {
    headers: {
      "Content-Type": "application/json",
      Authorization: `Bearer ${options.apiSecret}`,
    },
  });

  return res.data;
}

Generate Payment URL

First, write a method to generate the payment URL.

function buildPaymentURL(itemMemo: string, res: PaymentResponse): string {
  const urlSearchParams = new URLSearchParams();
  urlSearchParams.append("payID", res.payment.payID);
  urlSearchParams.append("brand", options.merchantBrand);
  urlSearchParams.append("memo", itemMemo);
  urlSearchParams.append("redirect_url", options.merchantRedirectURL);
  urlSearchParams.append("currency", "USD");
  const url = new URL(`${options.url}/payment_qrcode`);
  url.search = urlSearchParams.toString();
  return url.toString();
}
const amount = 100;
const createPaymentResponse = await createPayment(amount);
const paymentURL = buildPaymentURL("test item", createPaymentResponse);

User Payment

Display the generated paymentURL to the user, and when the user clicks on it, they will be directed to the payment page on the website. For the specific payment process, you can refer to the imsafu Payment Tutorial.

Retrieve Payment Information

After the user completes the payment, imsafu will send a POST request to the notifyURL provided when creating the order, with the payID included in the request body. We need to retrieve the payment information using the getPayment API and confirm whether the user's payment was successful.

To retrieve the payment information, we need to implement the getPayment method. This method takes the payment ID (payID) as a parameter and returns a Promise that resolves to a PaymentResponse object.

async function getPayment(payID: string): Promise<PaymentResponse> {
  const res = await axios.get<PaymentResponse>(
    `${options.api}/depositPays/${payID}`,
  );

  return res.data;
}
// Get the payID from the notify request

const paymentResponse = await getPayment(payID);

// Perform other operations

Appendix: Type Definitions Used in the Code

export interface Payment {
  payID: string;
  orderID: string;
  receiver: string;
  amount: string;
  originalAmount: string;
  maxFeeAmount: string;
  deadline: string;
}

export interface Chain {
  id: number;
  symbol: string;
  name: string;
}

export interface Token {
  symbol: string;
  address: string;
}

export interface ReceiveTx {
  chain: Chain;
  txID: string;
  confirmedAt: string;
  amount: string;
  feeAmount: string;
  token: Token;
}

export interface Deposit {
  chainID: number;
  token: string;
}

export interface PaymentResponse {
  status: string;
  payment: Payment;
  owner: string;
  depositAddress: string;
  callID: number;
  receiveTx: ReceiveTx | null;
  deposits: Deposit[] | null;
}

Please note that the above code examples are for demonstration purposes only. In actual usage, you should make appropriate adjustments and enhance security measures based on your specific requirements.

Last Updated:
Contributors: xavierdiff