Skip to main content

REST API Reference

MiniLedger exposes a RESTful HTTP API built on Hono. All responses are JSON-encoded. The API server starts on the port configured with --api-port (default 3000).

Base URL

http://localhost:3000

Conventions

  • All successful responses return a JSON body.
  • Paginated endpoints accept ?page=N&limit=M query parameters. The maximum limit is 100; the default is typically 20.
  • Error responses use standard HTTP status codes and include a JSON body with an error field:
    { "error": "Resource not found" }

Node

GET /status

Returns the current status of the node, including the blockchain height, connected peer count, and uptime.

Request

GET /status

Response 200 OK

{
"nodeId": "abc123def456",
"height": 142,
"peers": 2,
"uptime": 3600,
"consensus": "raft",
"role": "leader",
"version": "1.0.0"
}
FieldTypeDescription
nodeIdstringUnique identifier of this node
heightnumberCurrent blockchain height (latest block)
peersnumberNumber of currently connected peers
uptimenumberNode uptime in seconds
consensusstringActive consensus mechanism (raft, solo)
rolestringNode's consensus role
versionstringMiniLedger software version

GET /identity

Returns the cryptographic identity of this node.

Request

GET /identity

Response 200 OK

{
"nodeId": "abc123def456",
"publicKey": "04a1b2c3d4e5f6...",
"orgId": "my-org"
}
FieldTypeDescription
nodeIdstringUnique node identifier
publicKeystringNode's public key (hex-encoded)
orgIdstringOrganization identifier the node belongs to

GET /dashboard

Returns data for the web explorer dashboard, aggregating key metrics across blocks, transactions, peers, and consensus state.

Request

GET /dashboard

Response 200 OK

{
"height": 142,
"totalTransactions": 580,
"pendingTransactions": 3,
"peers": 2,
"consensus": {
"role": "leader",
"term": 5
},
"recentBlocks": [ ... ],
"recentTransactions": [ ... ]
}

Blocks

GET /blocks

Returns a paginated list of blocks, ordered by height descending.

Request

GET /blocks?page=1&limit=20
ParameterTypeDefaultDescription
pagenumber1Page number (1-indexed)
limitnumber20Items per page (max 100)

Response 200 OK

{
"blocks": [
{
"height": 142,
"hash": "a3f1b9c8d7e6...",
"previousHash": "f8e7d6c5b4a3...",
"timestamp": 1706000000000,
"transactions": 4,
"merkleRoot": "1a2b3c4d5e6f..."
}
],
"page": 1,
"limit": 20,
"total": 142
}
FieldTypeDescription
heightnumberBlock height in the chain
hashstringSHA-256 hash of the block
previousHashstringHash of the preceding block
timestampnumberUnix timestamp in milliseconds
transactionsnumberNumber of transactions in the block
merkleRootstringMerkle root of the block's transactions

GET /blocks/:height

Returns a single block by its height, including full transaction data.

Request

GET /blocks/42
ParameterTypeDescription
heightnumberBlock height

Response 200 OK

{
"height": 42,
"hash": "a3f1b9c8d7e6...",
"previousHash": "f8e7d6c5b4a3...",
"timestamp": 1706000000000,
"merkleRoot": "1a2b3c4d5e6f...",
"transactions": [
{
"hash": "b2c3d4e5f6a7...",
"type": "set",
"key": "account:alice",
"value": "{\"balance\":100}",
"sender": "04a1b2c3d4e5f6...",
"timestamp": 1706000000000
}
]
}

Error 404 Not Found

{ "error": "Block not found" }

GET /blocks/latest

Returns the most recently committed block.

Request

GET /blocks/latest

Response 200 OK

Returns the same shape as GET /blocks/:height.


Transactions

POST /tx

Submit a new transaction to the network. The transaction is added to the pending pool and will be included in the next block once consensus is reached.

Request

POST /tx
Content-Type: application/json

The body accepts two formats:

Key-Value format:

{
"key": "account:alice",
"value": "{\"balance\":150}"
}

Typed payload format:

{
"type": "transfer",
"payload": {
"from": "alice",
"to": "bob",
"amount": 50
}
}
FieldTypeRequiredDescription
keystringNo*State key to write
valuestringNo*Value to store (typically JSON-stringified)
typestringNo*Transaction type identifier
payloadobjectNo*Arbitrary transaction payload

*Either key+value or type+payload must be provided.

Response 201 Created

{
"hash": "b2c3d4e5f6a7...",
"status": "pending"
}
FieldTypeDescription
hashstringSHA-256 hash of the submitted transaction
statusstringAlways "pending" upon initial submission

Error 400 Bad Request

{ "error": "Invalid transaction: missing key or type" }

GET /tx

Returns the list of pending (unconfirmed) transactions in the mempool.

Request

GET /tx

Response 200 OK

{
"transactions": [
{
"hash": "b2c3d4e5f6a7...",
"type": "set",
"key": "account:alice",
"value": "{\"balance\":150}",
"sender": "04a1b2c3d4e5f6...",
"timestamp": 1706000000000,
"status": "pending"
}
],
"count": 1
}

GET /tx/:hash

Returns a single transaction by its hash. Works for both pending and confirmed transactions.

Request

GET /tx/b2c3d4e5f6a7...
ParameterTypeDescription
hashstringTransaction hash

Response 200 OK

{
"hash": "b2c3d4e5f6a7...",
"type": "set",
"key": "account:alice",
"value": "{\"balance\":150}",
"sender": "04a1b2c3d4e5f6...",
"timestamp": 1706000000000,
"status": "confirmed",
"blockHeight": 42,
"blockHash": "a3f1b9c8d7e6..."
}
FieldTypeDescription
hashstringTransaction hash
typestringTransaction type
keystringState key (if applicable)
valuestringStored value (if applicable)
senderstringPublic key of the sender
timestampnumberUnix timestamp in milliseconds
statusstring"pending" or "confirmed"
blockHeightnumberBlock height (only if confirmed)
blockHashstringBlock hash (only if confirmed)

Error 404 Not Found

{ "error": "Transaction not found" }

GET /tx/recent

Returns a paginated list of confirmed (committed) transactions, ordered by most recent first. Optionally filterable by transaction type.

Request

GET /tx/recent?page=1&limit=20&type=transfer
ParameterTypeDefaultDescription
pagenumber1Page number
limitnumber20Items per page (max 100)
typestringFilter by transaction type

Response 200 OK

{
"transactions": [
{
"hash": "b2c3d4e5f6a7...",
"type": "transfer",
"sender": "04a1b2c3d4e5f6...",
"timestamp": 1706000000000,
"status": "confirmed",
"blockHeight": 42
}
],
"page": 1,
"limit": 20,
"total": 580
}

GET /tx/sender/:pubkey

Returns all transactions sent by a specific public key, up to a maximum of 200 results.

Request

GET /tx/sender/04a1b2c3d4e5f6...
ParameterTypeDescription
pubkeystringSender's public key (hex)

Response 200 OK

{
"transactions": [ ... ],
"count": 24
}

State

GET /state

Returns a paginated list of all state entries. Internal keys (prefixed with _) are excluded from results.

Request

GET /state?page=1&limit=20
ParameterTypeDefaultDescription
pagenumber1Page number
limitnumber20Items per page (max 100)

Response 200 OK

{
"entries": [
{
"key": "account:alice",
"value": "{\"balance\":150}",
"updatedAt": 1706000000000,
"blockHeight": 42
}
],
"page": 1,
"limit": 20,
"total": 85
}
FieldTypeDescription
keystringState key
valuestringStored value
updatedAtnumberTimestamp of last update (ms)
blockHeightnumberBlock height of last update

GET /state/:key

Returns a single state entry by its key.

Request

GET /state/account:alice
ParameterTypeDescription
keystringState key

Response 200 OK

{
"key": "account:alice",
"value": "{\"balance\":150}",
"updatedAt": 1706000000000,
"blockHeight": 42
}

Error 404 Not Found

{ "error": "State entry not found" }

POST /state/query

Execute a SQL query against the state database. This provides a powerful way to filter, aggregate, and join state data.

Request

POST /state/query
Content-Type: application/json
{
"sql": "SELECT key, value FROM state WHERE key LIKE ? ORDER BY key",
"params": ["account:%"]
}
FieldTypeRequiredDescription
sqlstringYesSQL query string
paramsarrayNoParameterized query values

Response 200 OK

{
"results": [
{ "key": "account:alice", "value": "{\"balance\":150}" },
{ "key": "account:bob", "value": "{\"balance\":200}" }
],
"count": 2
}

Error 400 Bad Request

{ "error": "Invalid SQL query" }
caution

The SQL query endpoint operates in read-only mode. Only SELECT statements are permitted. Mutations (INSERT, UPDATE, DELETE, DROP) will be rejected.


Performs a unified search across blocks, transactions, state keys, and addresses. Useful for building block-explorer interfaces.

Request

GET /search?q=42
ParameterTypeRequiredDescription
qstringYesSearch term: block height, tx hash, state key, or address

Response 200 OK

{
"type": "block",
"result": {
"height": 42,
"hash": "a3f1b9c8d7e6...",
"timestamp": 1706000000000,
"transactions": 4
}
}

The type field indicates what was matched: "block", "transaction", "state", or "address". If nothing matches, the response returns:

{
"type": null,
"result": null
}

Peers

GET /peers

Returns the list of currently connected peers.

Request

GET /peers

Response 200 OK

{
"peers": [
{
"nodeId": "def456abc789",
"address": "192.168.1.10:4000",
"connectedAt": 1706000000000
},
{
"nodeId": "ghi789jkl012",
"address": "192.168.1.11:4000",
"connectedAt": 1706000050000
}
],
"count": 2
}
FieldTypeDescription
nodeIdstringPeer's unique node identifier
addressstringPeer's P2P address (host:port)
connectedAtnumberConnection timestamp (ms)

Consensus

GET /consensus

Returns the current consensus state of the node. Applicable when running Raft consensus.

Request

GET /consensus

Response 200 OK

{
"role": "leader",
"term": 5,
"leaderId": "abc123def456",
"votedFor": "abc123def456",
"commitIndex": 141,
"lastApplied": 141
}
FieldTypeDescription
rolestringCurrent role: "leader", "follower", or "candidate"
termnumberCurrent Raft term number
leaderIdstring|nullNode ID of the current leader
votedForstring|nullNode ID this node voted for in current term
commitIndexnumberIndex of highest committed log entry
lastAppliednumberIndex of highest applied log entry

Governance

GET /proposals

Returns all governance proposals.

Request

GET /proposals

Response 200 OK

{
"proposals": [
{
"id": "prop-001",
"title": "Increase block size limit",
"description": "Proposal to increase max transactions per block from 50 to 100.",
"status": "active",
"proposer": "04a1b2c3d4e5f6...",
"votesFor": 2,
"votesAgainst": 0,
"createdAt": 1706000000000
}
]
}

GET /proposals/:id

Returns a single governance proposal by its ID, including detailed vote information.

Request

GET /proposals/prop-001
ParameterTypeDescription
idstringProposal ID

Response 200 OK

{
"id": "prop-001",
"title": "Increase block size limit",
"description": "Proposal to increase max transactions per block from 50 to 100.",
"status": "active",
"proposer": "04a1b2c3d4e5f6...",
"votesFor": 2,
"votesAgainst": 0,
"votes": [
{
"voter": "04a1b2c3d4e5f6...",
"vote": "for",
"timestamp": 1706000000000
}
],
"createdAt": 1706000000000
}

Error 404 Not Found

{ "error": "Proposal not found" }

Contracts

GET /contracts

Returns all deployed smart contracts.

Request

GET /contracts

Response 200 OK

{
"contracts": [
{
"id": "contract-001",
"name": "TokenLedger",
"deployer": "04a1b2c3d4e5f6...",
"deployedAt": 1706000000000,
"blockHeight": 10
}
]
}

HTTP Status Codes

CodeMeaningUsage
200OKSuccessful read operation
201CreatedTransaction submitted successfully
400Bad RequestInvalid request body or query parameters
404Not FoundResource does not exist
500Internal Server ErrorUnexpected server-side failure

Rate Limiting

The REST API does not enforce rate limiting by default. In production deployments, consider placing MiniLedger behind a reverse proxy (e.g., Nginx, Caddy) with appropriate rate-limit rules.


CORS

The API server enables CORS for all origins by default, making it suitable for browser-based frontends and explorer dashboards.