Skip to content

Network configuration

MYRT is an ERC-20 token on an EVM chain. Which chain, how many confirmations an order needs, and the token address all depend on the host you are talking to. Read them from the API at startup. Never hardcode them.

Both calls on this page need a key with config:read. See scopes. The shapes are stated on the system reference.

Reading the configuration

GET/v1/configconfig:read

Returns the chains MYRT is issued on, the token decimals, and the paths of the order, balance and transaction endpoints.

bash
curl https://sandbox-api.myrt.money/v1/config \
  -H "Authorization: Bearer $MYRT_API_KEY"
ts
const res = await fetch("https://sandbox-api.myrt.money/v1/config", {
  headers: { Authorization: `Bearer ${process.env.MYRT_API_KEY}` },
});
const config = await res.json();
if (!config.ok) throw new Error(`${config.error.code}: ${config.error.message}`);
python
import os, requests

res = requests.get(
    "https://sandbox-api.myrt.money/v1/config",
    headers={"Authorization": f"Bearer {os.environ['MYRT_API_KEY']}"},
    timeout=30,
)
config = res.json()
if not config["ok"]:
    raise RuntimeError(f"{config['error']['code']}: {config['error']['message']}")

200 OK

json
{
  "ok": true,
  "apiVersion": "v1",
  "defaultChainId": 1,
  "decimals": 6,
  "chains": [
    {
      "key": "ethereum",
      "name": "Ethereum",
      "chainId": 1,
      "caip2": "eip155:1",
      "nativeCurrency": { "name": "Ether", "symbol": "ETH", "decimals": 18 },
      "explorerBaseUrl": "https://etherscan.io",
      "explorerAddressUrl": "https://etherscan.io/address/",
      "explorerTxUrl": "https://etherscan.io/tx/",
      "confirmations": 15,
      "myrt": { "address": "0x...", "decimals": 6, "name": "MYR Stablecoin", "symbol": "MYRT" }
    }
  ],
  "endpoints": {
    "mints": "/v1/mints",
    "redeems": "/v1/redeems",
    "transfers": "/v1/transfers",
    "balances": "/v1/balances/{walletAddress}",
    "transactions": "/v1/transactions/{referenceId}"
  }
}
FieldTypeDescription
apiVersionstringAlways v1
defaultChainIdnumberThe chain used when a request omits chainId
decimalsnumberMYRT decimals. Always 6
chains[]arrayOne entry per chain MYRT is issued on
chains[].chainIdnumberThe value to send as chainId on a request
chains[].caip2stringCAIP-2 identifier of the chain
chains[].nativeCurrencyobjectThe chain's own currency. Not MYRT
chains[].explorerAddressUrlstringPrefix for an explorer link to an address
chains[].explorerTxUrlstringPrefix for an explorer link to a transaction
chains[].confirmationsnumberConfirmations an order on this chain needs before it is completed
chains[].myrtobjectThe MYRT contract on this chain: address, decimals, name, symbol
endpointsobjectPaths of the order, balance and transaction endpoints, relative to the host

Read the configuration once at startup and cache it for the lifetime of the process.

A chainId on a request must be one of chains[].chainId. Omit chainId to use defaultChainId.

Chains

Sandbox and live are separate deployments on different chains. The hosts are listed under base URLs.

EnvironmentChainchainIdconfirmations
SandboxSepolia testnet111551113
LiveEthereum mainnet115

No real money moves on sandbox. It is a testnet deployment with test fiat rails.

confirmations is what stands between a transaction hash and a finished order. An order reaches status: "completed" only once its transaction has the chain's confirmation count. Until then it reports processing, even after blockchain.txHash is set. A transaction hash alone is not final. See order lifecycle.

TIP

Additional chains appear in /v1/config and /v1/tokens when they are enabled. Iterate over chains[] and tokens[] rather than assuming a single entry.

Token addresses

GET/v1/tokensconfig:read

Returns the MYRT token on each chain, with a ready-made explorer link.

bash
curl https://sandbox-api.myrt.money/v1/tokens \
  -H "Authorization: Bearer $MYRT_API_KEY"
ts
const res = await fetch("https://sandbox-api.myrt.money/v1/tokens", {
  headers: { Authorization: `Bearer ${process.env.MYRT_API_KEY}` },
});
const { tokens } = await res.json();
python
import os, requests

res = requests.get(
    "https://sandbox-api.myrt.money/v1/tokens",
    headers={"Authorization": f"Bearer {os.environ['MYRT_API_KEY']}"},
    timeout=30,
)
tokens = res.json()["tokens"]

200 OK

json
{
  "ok": true,
  "tokens": [
    { "symbol": "MYRT", "name": "MYR Stablecoin", "chainId": 1, "network": "Ethereum", "tokenAddress": "0x...", "decimals": 6, "explorerUrl": "https://etherscan.io/address/0x..." }
  ]
}

tokenAddress is the MYRT contract on that chain. It is the same value that orders and balance reads return as tokenAddress.

WARNING

The token address differs between sandbox and live. Never hardcode it. Read it from the host you are talking to; an address copied from one environment is wrong on the other.

Contract surface

MYRT is a standard ERC-20 token. A read-only integration, one that watches balances and confirms settlement on chain, needs only these:

Function or eventUse
balanceOfMYRT held by a wallet. Balance reads return the same value
decimalsAlways 6
symbolMYRT
totalSupplyTotal MYRT on that chain
Transfer eventEmitted by every mint, burn and transfer
text
event Transfer(address indexed from, address indexed to, uint256 value)
topic0: 0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef

A mint appears as a Transfer from the zero address to the recipient. A burn appears as a Transfer to the zero address. A transfer settled through this API appears as a standard Transfer to the recipient.

The event's value equals amounts.amountRaw on the order: amounts.myrt multiplied by 10^6, as an integer. Compare that, not the decimal string. See amounts.

Your integration never calls mint or burn on the contract. Issuance and redemption are reachable only through this API. See mint and redeem.

MYRT is a 1:1 Ringgit-backed stablecoin on Ethereum.