kepa
GETTING STARTED

Quickstart

Take a sandbox terminal from cold start to your first approved sale and webhook delivery in under ten minutes.

1

Provision a sandbox terminal

Sandbox terminals are free, instant, and behave identically to production. They run real EMV kernels against simulated card images and a mock acquirer.

Sign in at dashboard.atlas-softpos.com and click Provision sandbox terminal. You'll get a terminal ID and a sandbox API key (prefix sk_test_). Stash both in environment variables:

shell
export ATLAS_API_KEY="sk_test_..."
export BASE_URL="https://sandbox.atlas-softpos.com"
2

Confirm the terminal is reachable

Always health-check the terminal before trying to take a payment. The endpoint is cheap, idempotent, and surfaces network and firmware status in one call.

request
curl $BASE_URL/v1/device/health \
  -H "X-Api-Key: $ATLAS_API_KEY"
response
{
  "connected": true,
  "terminalId": "TID-SBX-00001",
  "firmwareVersion": "1.4.2",
  "connectivity": { "method": "WIFI", "signalStrength": -42 },
  "uptime": 86400
}
3

Run your first sale

Sandbox sales auto-approve unless you use one of the magic decline PANs. Note the Idempotency-Key — this is the safe-retry token that lets you survive network blips without double-charging.

request
curl $BASE_URL/v1/transaction/sale \
  -H "X-Api-Key: $ATLAS_API_KEY" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{
    "type": "SALE",
    "amount": 2500,
    "currency": "NZD",
    "referenceId": "DEMO-001"
  }'
response
{
  "transactionId": "txn_01JQXYZ123456",
  "status": "APPROVED",
  "type": "SALE",
  "amount": 2500,
  "currency": "NZD",
  "authorizationCode": "A12345",
  "responseCode": "00",
  "cardScheme": "VISA",
  "maskedPan": "************0002",
  "entryMode": "CONTACTLESS",
  "timestamp": "2026-04-08T11:14:22Z"
}

See Test Cards for the full set of sandbox PANs and decline scenarios.

4

Listen for the settlement webhook

Atlas delivers a signed webhook to your backend when the transaction settles, when a refund completes, when a dispute opens, and at end-of-day reconciliation. Always verify the signature before trusting the payload.

node.js + express
import express from "express";
import crypto from "crypto";

const app = express();
app.use(express.raw({ type: "application/json" }));

app.post("/atlas-webhook", (req, res) => {
  const sig = req.headers["atlas-signature"];
  const expected = crypto
    .createHmac("sha256", process.env.ATLAS_WEBHOOK_SECRET)
    .update(req.body)
    .digest("hex");

  if (sig !== `v1=${expected}`) {
    return res.status(401).end();
  }

  const event = JSON.parse(req.body);
  console.log("Received:", event.type, event.data.transactionId);
  res.status(200).end();
});

app.listen(4242);

Full event taxonomy and signature scheme on the Webhooks page.

5

Go live

When you're ready, swap your sandbox key for a live key (prefix sk_live_) and point your client at the production base URL. There are no code changes — same schema, same behavior, real funds.

production
export ATLAS_API_KEY="sk_live_..."
export BASE_URL="https://api.atlas-softpos.com"

Before flipping to production, walk through the Error reference and the Idempotency contract one more time.

NEXT

You now have a working integration end-to-end. Browse the Sale endpoint reference for the complete schema, or read Connectivity & Flows to understand how to switch between local, cloud, and embedded modes without changing your code.