AVC SMS

How to send SMS from Node.js in Sri Lanka

This tutorial sends SMS to Sri Lankan mobile numbers from Node.js using the AVC SMS REST API. It uses the fetch function that is built into Node.js 18 and later, so there is nothing to install. Your API key is on the Developer / API page of the portal after you create an account.

Developers3 min readUpdated

Send one SMS

Save this as sms.mjs and run it with AVCSMS_API_KEY=your_key node sms.mjs. The key stays in an environment variable, out of your code.

JavaScript
const API = 'https://avcsms.lk/api/v1';
const KEY = process.env.AVCSMS_API_KEY;

export async function sendSms(to, message, extra = {}) {
  const res = await fetch(`${API}/sms/send`, {
    method: 'POST',
    headers: { Authorization: `Bearer ${KEY}`, 'Content-Type': 'application/json' },
    body: JSON.stringify({ to, message, ...extra }),
  });
  const reply = await res.json();
  if (!res.ok) throw new Error(reply.message || `SMS request failed (HTTP ${res.status})`);
  return reply.data;
}

const result = await sendSms('0771234567', 'Your order #1042 is ready for pick-up.');
console.log(result.messages[0].id);   // keep this ID to check delivery later

A successful reply has HTTP status 201 and gives the cost, the number of parts, your new balance and an ID for each message. Numbers can be written as 0771234567, 94771234567 or +94771234567.

Send to many numbers, with names

Pass an array to send the same text to every number, up to 10,000 in one request. For a personal greeting, pass name-and-number pairs and write {name} in the message.

JavaScript
const result = await sendSms(
  [
    { to: '0771234567', name: 'Nimal' },
    { to: '0712345678', name: 'Kumari' },
  ],
  'Hi {name}, your November invoice is ready.',
  { sender_id: 'MYSHOP', ref: 'invoice-nov' },
);

console.log(`Accepted ${result.accepted} messages, cost Rs. ${result.cost}`);

The optional fields are sender_id (an approved sender ID on your account), ref (your own reference, returned in status replies), schedule_at (a date and time in Sri Lanka time, such as 2026-12-01 09:30) and callback_url (where the delivery report should go).

Check whether a message was delivered

JavaScript
export async function smsStatus(id) {
  const res = await fetch(`${API}/sms/${id}`, { headers: { Authorization: `Bearer ${KEY}` } });
  const reply = await res.json();
  if (!res.ok) throw new Error(reply.message);
  return reply.data;
}

console.log((await smsStatus(9001)).status);   // queued, sending, sent, delivered or failed

Receive delivery reports with Express

Set a webhook URL on the Developer / API page, or pass callback_url with a send. When a message is delivered or fails, your route receives a JSON report.

JavaScript
import express from 'express';

const app = express();
app.use(express.json());

app.post('/sms-status', (req, res) => {
  const { event, id, ref, to, status } = req.body;
  if (event === 'sms.status') {
    // update the order or login record that matches the reference
  }
  res.sendStatus(200);
});

app.listen(3000);
Each report is sent once. If your server was down, ask for the status of the message by its ID to catch up.

Good habits

  • Call the API from your server, never from code that runs in the browser or inside a mobile app, where anyone can read the key.
  • Restrict the key to the IP address of your server on the Developer / API page.
  • Treat HTTP 402 as "top up needed" and HTTP 429 as "slow down": each key can make 120 requests a minute.
  • Send campaigns as one request with many recipients instead of one request per number.

Every endpoint and field is in the SMS API reference, and how to add OTP verification by SMS shows the pattern for login codes.

More guides

All guides

Ready to send your first SMS?

Open an account in two minutes, or ask us for a volume quote.