Skip to content

Build USSD menus on a canvas. Publish them to your shortcode.

Asterisks keeps track of each session, speaks the request format of Hubtel, Nalo, Arkesel and Africa's Talking, and calls your API only where a screen needs your data.

Your first 100 sessions are free. After that, GHS 0.025 a session.

Dial *384*55# and press Call, then reply and press Send.

The same menu as it looks in the builder. The highlighted step is the screen on the phone.

Choice MenuWelcome
  1. 1 Check balanceEnd SessionShow balance
  2. 2 Send moneyAsk a QuestionRecipientAsk a QuestionAmountChoice MenuConfirmCollect PaymentCollect payment
  3. 3 Buy airtimeAsk a QuestionAirtime amountCollect PaymentCollect payment
  4. 0 ExitEnd SessionGoodbye

What the aggregator sends on each reply

text=""

Without a builder, every menu is an if statement on a string.

An aggregator sends the whole reply history on every request. Your handler splits it, works out which screen the user is on, and answers in that aggregator's format. Adding one option to a menu means renumbering the branches below it.

In Asterisks the screens are nodes and the branches are lines between them. The engine parses each aggregator's request and keeps the session, so your backend answers only the Send Data calls you add.

app.post('/ussd', async (req, res) => {
  const { phoneNumber, text } = req.body;
  const steps = text.split('*');

  if (text === '')
    return res.send('CON Asterisks Wallet\n1. Check balance\n2. Send money');
  if (text === '1')
    return res.send(`END Your balance is GHS ${await balance(phoneNumber)}`);
  if (steps[0] === '2' && steps.length === 2)
    return res.send('CON Enter amount (GHS)');
  if (steps[0] === '2' && steps.length === 3)
    return res.send(`CON Send GHS ${steps[2]} to ${steps[1]}?\n1. Confirm`);

  // ...then the same again in Hubtel's and Nalo's formats
});
A typical hand-written handler for the first two screens of the demo above.

Nine kinds of step cover most USSD services.

Balance checks, transfers, airtime, registrations and payments are built from the same parts.

Screens

Entry Point
Where a dial lands. One per flow.
Choice Menu
A numbered list. Each option is a line you draw to the next step.
Ask a Question
Free-text input, such as a phone number or an amount, saved to a variable.
Flash Alert
A message the user reads without replying.

Logic

Smart Router
If/else branching on variables or API results.
Sub-flow
A reusable piece, like a PIN check, shared across flows.

Actions

Send Data
Calls your API and puts the response in variables.
Collect Payment
Takes a mobile money or card payment.
End Session
Closes the session with a final message.

From empty canvas to live shortcode

  1. Step 1

    Lay out the flow

    Drag menus, questions and payments onto the canvas, or start from a template.

  2. Step 2

    Test it in the simulator

    Dial the flow on an on-screen phone and walk every branch before anyone else does.

  3. Step 3

    Connect your aggregator

    Add your shortcode and point your aggregator's callback at Asterisks.

  4. Step 4

    Publish

    The live flow updates on publish. Watch sessions arrive in the dashboard.

One flow, four aggregators.

Moving a flow to another aggregator is a settings change. Each one has a setup guide in the docs.

GHS 0.025

per completed session, paid from a prepaid wallet.

No monthly fee. The first 100 sessions are free, and Growth and Enterprise plans lower the rate at volume.