chore: initial commit for v0.0.1
DChain single-node blockchain + React Native messenger client. Core: - PBFT consensus with multi-sig validator admission + equivocation slashing - BadgerDB + schema migration scaffold (CurrentSchemaVersion=0) - libp2p gossipsub (tx/v1, blocks/v1, relay/v1, version/v1) - Native Go contracts (username_registry) alongside WASM (wazero) - WebSocket gateway with topic-based fanout + Ed25519-nonce auth - Relay mailbox with NaCl envelope encryption (X25519 + Ed25519) - Prometheus /metrics, per-IP rate limit, body-size cap Deployment: - Single-node compose (deploy/single/) with Caddy TLS + optional Prometheus - 3-node dev compose (docker-compose.yml) with mocked internet topology - 3-validator prod compose (deploy/prod/) for federation - Auto-update from Gitea via /api/update-check + systemd timer - Build-time version injection (ldflags → node --version) - UI / Swagger toggle flags (DCHAIN_DISABLE_UI, DCHAIN_DISABLE_SWAGGER) Client (client-app/): - Expo / React Native / NativeWind - E2E NaCl encryption, typing indicator, contact requests - Auto-discovery of canonical contracts, chain_id aware, WS reconnect on node switch Documentation: - README.md, CHANGELOG.md, CONTEXT.md - deploy/single/README.md with 6 operator scenarios - deploy/UPDATE_STRATEGY.md with 4-layer forward-compat design - docs/contracts/*.md per contract
This commit is contained in:
45
docs/api/README.md
Normal file
45
docs/api/README.md
Normal file
@@ -0,0 +1,45 @@
|
||||
# REST API
|
||||
|
||||
DChain-нода предоставляет HTTP API на порту `--stats-addr` (по умолчанию `:8080`).
|
||||
|
||||
## Базовые URL
|
||||
|
||||
| Окружение | URL |
|
||||
|---------|-----|
|
||||
| Локально | `http://localhost:8081` |
|
||||
| Docker node1 | `http://node1:8080` |
|
||||
| Docker node2 | `http://node2:8080` |
|
||||
| Docker node3 | `http://node3:8080` |
|
||||
|
||||
## Разделы API
|
||||
|
||||
| Документ | Эндпоинты |
|
||||
|---------|----------|
|
||||
| [Chain API](chain.md) | Блоки, транзакции, балансы, адреса, stats |
|
||||
| [Contracts API](contracts.md) | Деплой, вызов, state, логи |
|
||||
| [Relay API](relay.md) | Отправка сообщений, inbox, контакты |
|
||||
|
||||
## Формат ошибок
|
||||
|
||||
```json
|
||||
{"error": "описание ошибки"}
|
||||
```
|
||||
|
||||
HTTP-статус: 400 для клиентских ошибок, 500 для серверных.
|
||||
|
||||
## Аутентификация
|
||||
|
||||
REST API не требует аутентификации. Транзакции подписываются на стороне клиента (CLI-командами) и отправляются как подписанные JSON-объекты. API не имеет admin-эндпоинтов требующих токенов.
|
||||
|
||||
## Пример
|
||||
|
||||
```bash
|
||||
# Статистика сети
|
||||
curl http://localhost:8081/api/stats
|
||||
|
||||
# Баланс адреса
|
||||
curl http://localhost:8081/api/balance/03a1b2c3...
|
||||
|
||||
# Последние блоки
|
||||
curl http://localhost:8081/api/blocks?limit=10
|
||||
```
|
||||
314
docs/api/chain.md
Normal file
314
docs/api/chain.md
Normal file
@@ -0,0 +1,314 @@
|
||||
# Chain API
|
||||
|
||||
Эндпоинты для чтения блокчейна: блоки, транзакции, балансы, идентичности, валидаторы.
|
||||
|
||||
## Статистика сети
|
||||
|
||||
### `GET /api/netstats`
|
||||
|
||||
Агрегированная статистика сети.
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/netstats
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"total_blocks": 1024,
|
||||
"total_txs": 4821,
|
||||
"validator_count": 3,
|
||||
"relay_count": 1,
|
||||
"total_supply_ut": 10000000000
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Блоки
|
||||
|
||||
### `GET /api/blocks?limit=N`
|
||||
|
||||
Последние `N` блоков (по умолчанию 20).
|
||||
|
||||
```bash
|
||||
curl "http://localhost:8081/api/blocks?limit=10"
|
||||
```
|
||||
|
||||
```json
|
||||
[
|
||||
{
|
||||
"index": 1024,
|
||||
"hash": "a1b2c3...",
|
||||
"prev_hash": "...",
|
||||
"timestamp": 1710000000,
|
||||
"validator": "03abcd...",
|
||||
"tx_count": 3,
|
||||
"total_fees_ut": 15000
|
||||
},
|
||||
...
|
||||
]
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### `GET /api/block/{index}`
|
||||
|
||||
Детали блока по высоте.
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/block/1024
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"index": 1024,
|
||||
"hash": "a1b2c3...",
|
||||
"prev_hash": "...",
|
||||
"timestamp": 1710000000,
|
||||
"validator": "03abcd...",
|
||||
"transactions": [
|
||||
{
|
||||
"id": "tx-abc123",
|
||||
"type": "TRANSFER",
|
||||
"from": "03...",
|
||||
"to": "04...",
|
||||
"amount_ut": 1000000,
|
||||
"fee_ut": 1000
|
||||
}
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Транзакции
|
||||
|
||||
### `GET /api/txs/recent?limit=N`
|
||||
|
||||
Последние транзакции (по умолчанию 20).
|
||||
|
||||
```bash
|
||||
curl "http://localhost:8081/api/txs/recent?limit=5"
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### `GET /api/tx/{txid}`
|
||||
|
||||
Транзакция по ID.
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/tx/tx-abc123def456
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"id": "tx-abc123",
|
||||
"block_index": 1024,
|
||||
"type": "CALL_CONTRACT",
|
||||
"from": "03abcd...",
|
||||
"timestamp": 1710000000,
|
||||
"payload": { ... },
|
||||
"signature": "..."
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### `POST /api/tx`
|
||||
|
||||
Отправить подписанную транзакцию.
|
||||
|
||||
```bash
|
||||
curl -X POST http://localhost:8081/api/tx \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{"type":"TRANSFER","from":"03...","payload":{...},"signature":"..."}'
|
||||
```
|
||||
|
||||
```json
|
||||
{"id": "tx-abc123", "status": "accepted"}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Chain API v2
|
||||
|
||||
Расширенный API для работы с транзакциями.
|
||||
|
||||
### `GET /v2/chain/transactions/{tx_id}`
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/v2/chain/transactions/tx-abc123
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"id": "tx-abc123",
|
||||
"block_index": 1024,
|
||||
"payload": { ... },
|
||||
"payload_hex": "...",
|
||||
"signature_hex": "..."
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### `GET /v2/chain/accounts/{account_id}/transactions`
|
||||
|
||||
Транзакции для аккаунта с пагинацией.
|
||||
|
||||
**Query параметры:**
|
||||
| Параметр | По умолчанию | Описание |
|
||||
|---------|------------|---------|
|
||||
| `limit` | 100 | Максимум (max 1000) |
|
||||
| `after_block` | — | Только блоки после N |
|
||||
| `before_block` | — | Только блоки до N |
|
||||
| `order` | `desc` | `asc` или `desc` |
|
||||
|
||||
```bash
|
||||
curl "http://localhost:8081/v2/chain/accounts/03abcd.../transactions?limit=20&order=desc"
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### `POST /v2/chain/transactions/draft`
|
||||
|
||||
Создать черновик транзакции для подписания.
|
||||
|
||||
```bash
|
||||
curl -X POST http://localhost:8081/v2/chain/transactions/draft \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{"from":"03...","to":"04...","amount_ut":1000000}'
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"tx": { ... },
|
||||
"sign_bytes_hex": "...",
|
||||
"sign_bytes_base64": "..."
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### `POST /v2/chain/transactions`
|
||||
|
||||
Отправить подписанную транзакцию (расширенный формат).
|
||||
|
||||
```bash
|
||||
curl -X POST http://localhost:8081/v2/chain/transactions \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{"tx":{...},"signature":"..."}'
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Адреса
|
||||
|
||||
### `GET /api/address/{addr}?limit=N&offset=N`
|
||||
|
||||
Информация об адресе (DC-адрес или hex pubkey).
|
||||
|
||||
```bash
|
||||
curl "http://localhost:8081/api/address/DCabc123?limit=20&offset=0"
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"address": "DCabc123...",
|
||||
"pub_key": "03abcd...",
|
||||
"balance_ut": 9500000,
|
||||
"tx_count": 12,
|
||||
"transactions": [...],
|
||||
"has_more": false
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Идентичности и валидаторы
|
||||
|
||||
### `GET /api/identity/{pubkey|addr}`
|
||||
|
||||
Информация об идентичности.
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/identity/03abcd...
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"pub_key": "03abcd...",
|
||||
"address": "DCabc123...",
|
||||
"nick": "alice",
|
||||
"x25519_pub": "...",
|
||||
"registered_at": 100,
|
||||
"stake_ut": 1000000000
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### `GET /api/validators`
|
||||
|
||||
Список активных валидаторов.
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/validators
|
||||
```
|
||||
|
||||
```json
|
||||
[
|
||||
{"pub_key": "03...", "stake_ut": 1000000000},
|
||||
{"pub_key": "04...", "stake_ut": 1000000000}
|
||||
]
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### `GET /api/node/{pubkey|addr}?window=N`
|
||||
|
||||
Информация об узле (статистика, репутация).
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/node/03abcd...
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### `GET /api/relays`
|
||||
|
||||
Зарегистрированные relay-провайдеры.
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/relays
|
||||
```
|
||||
|
||||
```json
|
||||
[
|
||||
{
|
||||
"pub_key": "03...",
|
||||
"relay_pub": "...",
|
||||
"fee_ut": 100,
|
||||
"endpoint": ""
|
||||
}
|
||||
]
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Live Events
|
||||
|
||||
### `GET /api/events`
|
||||
|
||||
Server-Sent Events поток новых блоков и транзакций.
|
||||
|
||||
```bash
|
||||
curl -N http://localhost:8081/api/events
|
||||
```
|
||||
|
||||
```
|
||||
data: {"type":"block","index":1025,"hash":"...","tx_count":2}
|
||||
|
||||
data: {"type":"tx","id":"tx-abc","block":1025,"from":"03..."}
|
||||
```
|
||||
285
docs/api/contracts.md
Normal file
285
docs/api/contracts.md
Normal file
@@ -0,0 +1,285 @@
|
||||
# Contracts API
|
||||
|
||||
REST API для работы с WASM-контрактами: деплой, вызов, чтение state и логов.
|
||||
|
||||
> Деплой и вызов контрактов выполняются через CLI-команды `client deploy-contract` и `client call-contract`, которые формируют и отправляют подписанные транзакции через `POST /api/tx`. Прямой HTTP-деплой не поддерживается.
|
||||
|
||||
## Список контрактов
|
||||
|
||||
### `GET /api/contracts`
|
||||
|
||||
Все задеплоенные контракты.
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/contracts
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"count": 4,
|
||||
"contracts": [
|
||||
{
|
||||
"contract_id": "a1b2c3d4e5f60001",
|
||||
"deployer_pub": "03abcd...",
|
||||
"deployed_at": 100,
|
||||
"wasm_size": 1842,
|
||||
"abi": {
|
||||
"contract": "governance",
|
||||
"version": "1.0.0",
|
||||
"methods": [...]
|
||||
}
|
||||
},
|
||||
...
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Детали контракта
|
||||
|
||||
### `GET /api/contracts/{contractID}`
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/contracts/a1b2c3d4e5f60001
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"contract_id": "a1b2c3d4e5f60001",
|
||||
"deployer_pub": "03abcd...",
|
||||
"deployed_at": 100,
|
||||
"wasm_size": 1842,
|
||||
"abi_json": "{...}"
|
||||
}
|
||||
```
|
||||
|
||||
| Поле | Тип | Описание |
|
||||
|------|-----|---------|
|
||||
| `contract_id` | string | 16-символьный hex ID |
|
||||
| `deployer_pub` | string | Pubkey деплоера |
|
||||
| `deployed_at` | uint64 | Высота блока деплоя |
|
||||
| `wasm_size` | int | Размер WASM в байтах |
|
||||
| `abi_json` | string | JSON ABI контракта |
|
||||
|
||||
---
|
||||
|
||||
## State контракта
|
||||
|
||||
### `GET /api/contracts/{contractID}/state/{key}`
|
||||
|
||||
Читает значение из state контракта по ключу.
|
||||
|
||||
```bash
|
||||
# Строковое значение
|
||||
curl http://localhost:8081/api/contracts/a1b2c3d4e5f60001/state/admin
|
||||
|
||||
# Вложенный ключ
|
||||
curl "http://localhost:8081/api/contracts/a1b2c3d4e5f60001/state/param:gas_price"
|
||||
|
||||
# Ключ эскроу
|
||||
curl "http://localhost:8081/api/contracts/.../state/e:deal-001:b"
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"key": "admin",
|
||||
"value_b64": "MDNhYmNk...",
|
||||
"value_hex": "30336162636...",
|
||||
"value_u64": null
|
||||
}
|
||||
```
|
||||
|
||||
| Поле | Тип | Описание |
|
||||
|------|-----|---------|
|
||||
| `value_b64` | string | Base64-encoded raw bytes |
|
||||
| `value_hex` | string | Hex-encoded raw bytes |
|
||||
| `value_u64` | uint64\|null | Если значение ровно 8 байт big-endian |
|
||||
|
||||
**Примеры чтения state контрактов:**
|
||||
|
||||
```bash
|
||||
# Governance: live параметр
|
||||
curl "http://localhost:8081/api/contracts/$GOV_ID/state/param:gas_price"
|
||||
|
||||
# Governance: pending предложение
|
||||
curl "http://localhost:8081/api/contracts/$GOV_ID/state/prop:gas_price"
|
||||
|
||||
# Username registry: pubkey по имени
|
||||
curl "http://localhost:8081/api/contracts/$REG_ID/state/name:alice"
|
||||
# value_hex = hex(pubkey_bytes) → hex.DecodeString(value_hex) = pubkey
|
||||
|
||||
# Escrow: статус сделки
|
||||
curl "http://localhost:8081/api/contracts/$ESC_ID/state/e:deal-001:x"
|
||||
# value_hex: 61='a' (active), 64='d' (disputed), 72='r' (released), 66='f' (refunded)
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Логи контракта
|
||||
|
||||
### `GET /api/contracts/{contractID}/logs?limit=N`
|
||||
|
||||
Последние `N` лог-записей (по умолчанию 50, максимум 100).
|
||||
|
||||
```bash
|
||||
curl "http://localhost:8081/api/contracts/a1b2c3d4e5f60001/logs?limit=20"
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"contract_id": "a1b2c3d4e5f60001",
|
||||
"count": 5,
|
||||
"logs": [
|
||||
{
|
||||
"tx_id": "tx-abc123",
|
||||
"block_index": 1024,
|
||||
"timestamp": 1710000000,
|
||||
"message": "registered: alice"
|
||||
},
|
||||
{
|
||||
"tx_id": "tx-def456",
|
||||
"block_index": 1020,
|
||||
"timestamp": 1709999800,
|
||||
"message": "initialized"
|
||||
}
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
Логи отсортированы от новейших к старейшим.
|
||||
|
||||
---
|
||||
|
||||
## Деплой контракта (через CLI)
|
||||
|
||||
```bash
|
||||
client deploy-contract \
|
||||
--key key.json \
|
||||
--wasm mycontract.wasm \
|
||||
--abi mycontract_abi.json \
|
||||
--node http://localhost:8081
|
||||
```
|
||||
|
||||
Успешный деплой печатает:
|
||||
```
|
||||
contract_id: a1b2c3d4e5f60001
|
||||
```
|
||||
|
||||
В Docker:
|
||||
```bash
|
||||
docker exec node1 client deploy-contract \
|
||||
--key /keys/node1.json \
|
||||
--wasm /contracts/mycontract.wasm \
|
||||
--abi /contracts/mycontract_abi.json \
|
||||
--node http://node1:8080
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Вызов контракта (через CLI)
|
||||
|
||||
```bash
|
||||
# Без аргументов
|
||||
client call-contract \
|
||||
--contract a1b2c3d4e5f60001 \
|
||||
--method increment \
|
||||
--gas 5000 \
|
||||
--key key.json --node http://localhost:8081
|
||||
|
||||
# Строковый аргумент
|
||||
client call-contract \
|
||||
--contract $REG_ID \
|
||||
--method register \
|
||||
--arg alice \
|
||||
--gas 30000 \
|
||||
--key key.json --node http://localhost:8081
|
||||
|
||||
# Числовой аргумент (uint64)
|
||||
client call-contract \
|
||||
--contract $ESC_ID \
|
||||
--method create \
|
||||
--arg "deal-001" \
|
||||
--arg "$SELLER_PUB" \
|
||||
--arg64 5000000 \
|
||||
--gas 30000 \
|
||||
--key key.json --node http://localhost:8081
|
||||
|
||||
# Несколько аргументов в JSON
|
||||
client call-contract \
|
||||
--contract $AUCTION_ID \
|
||||
--method create \
|
||||
--args '["Rare item #1", 1000000, 100]' \
|
||||
--gas 20000 \
|
||||
--key key.json --node http://localhost:8081
|
||||
```
|
||||
|
||||
### Флаги call-contract
|
||||
|
||||
| Флаг | Тип | Описание |
|
||||
|------|-----|---------|
|
||||
| `--contract` | string | ID контракта (16 hex) |
|
||||
| `--method` | string | Имя метода |
|
||||
| `--arg` | string | Добавить строковый аргумент (повторяемый) |
|
||||
| `--arg64` | uint64 | Добавить числовой аргумент (повторяемый) |
|
||||
| `--args` | JSON | Массив всех аргументов `["str", 42, ...]` |
|
||||
| `--gas` | uint64 | Gas лимит |
|
||||
| `--key` | path | Файл ключа |
|
||||
| `--node` | URL | Node URL |
|
||||
|
||||
---
|
||||
|
||||
## Токены и NFT
|
||||
|
||||
### `GET /api/tokens`
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/tokens
|
||||
```
|
||||
|
||||
```json
|
||||
{"count": 2, "tokens": [{...}]}
|
||||
```
|
||||
|
||||
### `GET /api/tokens/{id}`
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/tokens/abc123
|
||||
```
|
||||
|
||||
### `GET /api/tokens/{id}/balance/{pubkey}`
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/tokens/abc123/balance/03abcd...
|
||||
```
|
||||
|
||||
```json
|
||||
{
|
||||
"token_id": "abc123",
|
||||
"pub_key": "03abcd...",
|
||||
"address": "DCabc...",
|
||||
"balance": 1000
|
||||
}
|
||||
```
|
||||
|
||||
### `GET /api/nfts`
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/nfts
|
||||
```
|
||||
|
||||
### `GET /api/nfts/{id}`
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/nfts/nft-abc123
|
||||
```
|
||||
|
||||
### `GET /api/nfts/owner/{pubkey}`
|
||||
|
||||
```bash
|
||||
curl http://localhost:8081/api/nfts/owner/03abcd...
|
||||
```
|
||||
|
||||
```json
|
||||
{"count": 3, "nfts": [{...}]}
|
||||
```
|
||||
246
docs/api/relay.md
Normal file
246
docs/api/relay.md
Normal file
@@ -0,0 +1,246 @@
|
||||
# Relay API
|
||||
|
||||
REST API для работы с шифрованными сообщениями через relay-сеть.
|
||||
|
||||
Сообщения шифруются E2E с использованием NaCl (X25519 + XSalsa20-Poly1305). Relay хранит зашифрованные конверты и доставляет их получателям.
|
||||
|
||||
## Отправить сообщение
|
||||
|
||||
### `POST /relay/send`
|
||||
|
||||
Зашифровать и отправить сообщение получателю.
|
||||
|
||||
**Request body:**
|
||||
```json
|
||||
{
|
||||
"recipient_pub": "<x25519_hex>",
|
||||
"msg_b64": "<base64_encoded_message>"
|
||||
}
|
||||
```
|
||||
|
||||
| Поле | Тип | Описание |
|
||||
|------|-----|---------|
|
||||
| `recipient_pub` | string | X25519 public key получателя (hex) |
|
||||
| `msg_b64` | string | Сообщение в base64 |
|
||||
|
||||
```bash
|
||||
MSG=$(echo -n "Hello, Bob!" | base64)
|
||||
curl -X POST http://localhost:8081/relay/send \
|
||||
-H "Content-Type: application/json" \
|
||||
-d "{\"recipient_pub\":\"$BOB_X25519\",\"msg_b64\":\"$MSG\"}"
|
||||
```
|
||||
|
||||
**Response:**
|
||||
```json
|
||||
{
|
||||
"id": "env-abc123",
|
||||
"recipient_pub": "...",
|
||||
"status": "sent"
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Broadcast конверта
|
||||
|
||||
### `POST /relay/broadcast`
|
||||
|
||||
Опубликовать pre-sealed конверт (для light-клиентов, которые шифруют на своей стороне).
|
||||
|
||||
**Request body:**
|
||||
```json
|
||||
{
|
||||
"envelope": {
|
||||
"id": "...",
|
||||
"recipient_pub": "...",
|
||||
"sender_pub": "...",
|
||||
"payload_b64": "...",
|
||||
"timestamp": 1710000000,
|
||||
"fee_ut": 100
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
```bash
|
||||
curl -X POST http://localhost:8081/relay/broadcast \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{"envelope": {...}}'
|
||||
```
|
||||
|
||||
**Response:**
|
||||
```json
|
||||
{"id": "env-abc123", "status": "broadcast"}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Inbox
|
||||
|
||||
### `GET /relay/inbox?pub=<x25519hex>&since=<ts>&limit=N`
|
||||
|
||||
Получить сообщения из inbox.
|
||||
|
||||
**Query параметры:**
|
||||
| Параметр | Обязательный | Описание |
|
||||
|---------|------------|---------|
|
||||
| `pub` | Да | X25519 pubkey получателя (hex) |
|
||||
| `since` | Нет | Unix timestamp — только сообщения новее |
|
||||
| `limit` | Нет | Максимум (по умолчанию 50) |
|
||||
|
||||
```bash
|
||||
# Получить все сообщения
|
||||
curl "http://localhost:8081/relay/inbox?pub=$MY_X25519"
|
||||
|
||||
# Только новые (после timestamp)
|
||||
curl "http://localhost:8081/relay/inbox?pub=$MY_X25519&since=1710000000&limit=20"
|
||||
```
|
||||
|
||||
**Response:**
|
||||
```json
|
||||
{
|
||||
"pub": "...",
|
||||
"count": 2,
|
||||
"has_more": false,
|
||||
"items": [
|
||||
{
|
||||
"id": "env-abc123",
|
||||
"sender_pub": "...",
|
||||
"payload_b64": "...",
|
||||
"timestamp": 1710000000,
|
||||
"fee_ut": 100
|
||||
}
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
> `payload_b64` содержит зашифрованное сообщение. Расшифровка выполняется на стороне клиента с помощью X25519 private key.
|
||||
|
||||
---
|
||||
|
||||
### `GET /relay/inbox/count?pub=<hex>`
|
||||
|
||||
Количество сообщений в inbox.
|
||||
|
||||
```bash
|
||||
curl "http://localhost:8081/relay/inbox/count?pub=$MY_X25519"
|
||||
```
|
||||
|
||||
**Response:**
|
||||
```json
|
||||
{"pub": "...", "count": 3}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### `DELETE /relay/inbox/{envID}?pub=<hex>`
|
||||
|
||||
Удалить сообщение из inbox.
|
||||
|
||||
```bash
|
||||
curl -X DELETE "http://localhost:8081/relay/inbox/env-abc123?pub=$MY_X25519"
|
||||
```
|
||||
|
||||
**Response:**
|
||||
```json
|
||||
{"id": "env-abc123", "status": "deleted"}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Контакты
|
||||
|
||||
### `GET /relay/contacts?pub=<ed25519hex>`
|
||||
|
||||
Входящие запросы на контакт.
|
||||
|
||||
> Используйте **ed25519** pubkey (не X25519).
|
||||
|
||||
```bash
|
||||
curl "http://localhost:8081/relay/contacts?pub=$MY_ED25519"
|
||||
```
|
||||
|
||||
**Response:**
|
||||
```json
|
||||
{
|
||||
"pub": "...",
|
||||
"count": 1,
|
||||
"contacts": [
|
||||
{
|
||||
"from_pub": "03abcd...",
|
||||
"from_nick": "alice",
|
||||
"intro": "Hi! Let's connect.",
|
||||
"fee_ut": 1000,
|
||||
"timestamp": 1710000000
|
||||
}
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## CLI команды для relay
|
||||
|
||||
Прямой вызов relay API через CLI:
|
||||
|
||||
```bash
|
||||
# Отправить сообщение (автоматически ищет X25519 ключ в registry)
|
||||
client send-msg \
|
||||
--to $RECIPIENT_PUB \
|
||||
--msg "Hello!" \
|
||||
--key key.json \
|
||||
--node http://localhost:8081
|
||||
|
||||
# Отправить через @username
|
||||
client send-msg \
|
||||
--to @alice \
|
||||
--msg "Hello Alice!" \
|
||||
--registry $REGISTRY_ID \
|
||||
--key key.json \
|
||||
--node http://localhost:8081
|
||||
|
||||
# Получить сообщения из inbox
|
||||
client inbox \
|
||||
--key key.json \
|
||||
--node http://localhost:8081 \
|
||||
--limit 20
|
||||
|
||||
# Удалить прочитанные
|
||||
client inbox \
|
||||
--key key.json \
|
||||
--node http://localhost:8081 \
|
||||
--delete
|
||||
|
||||
# Запросить контакт
|
||||
client request-contact \
|
||||
--to $RECIPIENT_PUB \
|
||||
--fee 1000 \
|
||||
--intro "Hi, I want to connect" \
|
||||
--key key.json \
|
||||
--node http://localhost:8081
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Архитектура relay
|
||||
|
||||
```
|
||||
Отправитель Relay Node Получатель
|
||||
│ │ │
|
||||
│── POST /relay/send ───────────────▶│ │
|
||||
│ {recipient_pub, msg_b64} │ Encrypt (NaCl box) │
|
||||
│ │ Broadcast via gossipsub │
|
||||
│ │◀── gossip ─────────────────▶│
|
||||
│ │ │
|
||||
│ │ Store in mailbox │
|
||||
│ │ │
|
||||
│ │◀── GET /relay/inbox?pub=... ─│
|
||||
│ │ │
|
||||
│ │─── {items:[{payload_b64}]} ▶│
|
||||
│ │ │
|
||||
│ │ Submit RELAY_PROOF tx │
|
||||
│ │ (claim fee from sender) │
|
||||
```
|
||||
|
||||
**Gossipsub топик:** `dchain/relay/v1`
|
||||
|
||||
**Fee:** Relay берёт fee (задаётся при регистрации `--relay-fee`). Sender должен иметь достаточный баланс. Fee списывается при доставке через RELAY_PROOF транзакцию.
|
||||
Reference in New Issue
Block a user