Feat/add networks (#1303)

* No commit suggestions generated

* No commit suggestions generated

* No commit suggestions generated
This commit is contained in:
Prad Nukala
2025-10-12 11:23:20 -04:00
committed by GitHub
parent 40eadc995e
commit ebfa2b062a
97 changed files with 3979 additions and 16119 deletions
+17
View File
@@ -0,0 +1,17 @@
CHAIN_ID=sonrtest_1-1
DENOM=usnr
KEYRING=test
KEYALGO=eth_secp256k1
BLOCK_TIME=5s
VOTING_PERIOD=30s
EXPEDITED_VOTING_PERIOD=15s
MAX_GAS=100000000
MIN_COMMISSION_RATE=0.050000000000000000
NARUTO_MNEMONIC="decorate bright ozone fork gallery riot bus exhaust worth way bone indoor calm squirrel merry zero scheme cotton until shop any excess stage laundry"
SENKU_MNEMONIC="wealth flavor believe regret funny network recall kiss grape useless pepper cram hint member few certain unveil rather brick bargain curious require crowd raise"
YAEGER_MNEMONIC="quality vacuum heart guard buzz spike sight swarm shove special gym robust assume sudden deposit grid alcohol choice devote leader tilt noodle tide penalty"
FAUCET_MNEMONIC="notice oak worry limit wrap speak medal online prefer cluster roof addict wrist behave treat actual wasp year salad speed social layer crew genius"
BASE_ALLOCATION=100000000000000000000000000usnr
STAKE_AMOUNT=30000000000000000000000usnr
FAUCET_ALLOCATION=250000000000000000000000000000usnr
DOCKER_IMAGE=onsonr/snrd:latest
+106
View File
@@ -0,0 +1,106 @@
name: sonr-core
services:
ipfs:
container_name: ipfs
image: ipfs/kubo:release
ports:
- "127.0.0.1:5001:5001"
- "127.0.0.1:8080:8080"
- "127.0.0.1:4001:4001"
volumes:
- ${HOME}/.ipfs:/data/ipfs
networks:
- sonr-network
cluster:
container_name: cluster
image: ipfs/ipfs-cluster:latest
depends_on:
- ipfs
environment:
CLUSTER_PEERNAME: cluster
CLUSTER_SECRET: 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
CLUSTER_IPFSHTTP_NODEMULTIADDRESS: /dns4/ipfs/tcp/5001
CLUSTER_CRDT_TRUSTEDPEERS: "*"
CLUSTER_MONITORPINGINTERVAL: 2s
ports:
- "127.0.0.1:9094:9094"
- "127.0.0.1:9095:9095"
volumes:
- ${HOME}/.ipfs-cluster:/data/ipfs-cluster
networks:
- sonr-network
caddy:
container_name: caddy
image: caddy:2-alpine
restart: unless-stopped
depends_on:
snrd:
condition: service_healthy
ports:
- "80:80"
- "443:443"
- "443:443/udp"
volumes:
- ./caddy/Caddyfile:/etc/caddy/Caddyfile:ro
- caddy-data:/data
- caddy-config:/config
environment:
CADDY_DOMAIN: ${CADDY_DOMAIN:-localhost}
networks:
- sonr-network
snrd:
container_name: snrd
image: onsonr/snrd:latest
build:
context: .
dockerfile: cmd/snrd/Dockerfile
restart: unless-stopped
depends_on:
- ipfs
command: ["/usr/bin/devnet"]
environment:
CHAIN_ID: ${CHAIN_ID:-sonrtest_1-1}
MONIKER: ${MONIKER:-sonr-dev-node}
DENOM: ${DENOM:-usnr}
BLOCK_TIME: ${BLOCK_TIME:-1s}
CLEAN: ${CLEAN:-true}
KEYRING: ${KEYRING:-test}
HOME_DIR: /home/snrd/.snrd
KEY: acc0
KEY2: acc1
KEYALGO: eth_secp256k1
LOG_LEVEL: ${LOG_LEVEL:-debug}
TRACE: ${TRACE:-true}
SKIP_INSTALL: "true"
ports:
- "26657:26657"
- "1317:1317"
- "9090:9090"
- "9091:9091"
- "8545:8545"
- "8546:8546"
- "26656:26656"
- "6060:6060"
volumes:
- ${HOME}/.sonr:/root/.sonr
healthcheck:
test: ["CMD", "snrd", "status", "--home", "/home/snrd/.snrd"]
interval: 10s
timeout: 5s
retries: 5
start_period: 60s
networks:
- sonr-network
networks:
sonr-network:
driver: bridge
name: sonr-network
volumes:
caddy-config:
caddy-data:
+17
View File
@@ -0,0 +1,17 @@
CHAIN_ID=sonrtest_1-1
DENOM=usnr
KEYRING=test
KEYALGO=eth_secp256k1
BLOCK_TIME=5s
VOTING_PERIOD=30s
EXPEDITED_VOTING_PERIOD=15s
MAX_GAS=100000000
MIN_COMMISSION_RATE=0.050000000000000000
NARUTO_MNEMONIC="decorate bright ozone fork gallery riot bus exhaust worth way bone indoor calm squirrel merry zero scheme cotton until shop any excess stage laundry"
SENKU_MNEMONIC="wealth flavor believe regret funny network recall kiss grape useless pepper cram hint member few certain unveil rather brick bargain curious require crowd raise"
YAEGER_MNEMONIC="quality vacuum heart guard buzz spike sight swarm shove special gym robust assume sudden deposit grid alcohol choice devote leader tilt noodle tide penalty"
FAUCET_MNEMONIC="notice oak worry limit wrap speak medal online prefer cluster roof addict wrist behave treat actual wasp year salad speed social layer crew genius"
BASE_ALLOCATION=100000000000000000000000000usnr
STAKE_AMOUNT=30000000000000000000000usnr
FAUCET_ALLOCATION=250000000000000000000000000000usnr
DOCKER_IMAGE=onsonr/snrd:latest
+591
View File
@@ -0,0 +1,591 @@
# Docker Containers
This document describes all Docker containers used in the Sonr testnet architecture.
## Overview
The testnet consists of 7 containers organized in a validator-sentry architecture:
- **3 Validators** (private, isolated networks)
- **3 Sentry Nodes** (public-facing, Cloudflare tunnel integration)
- **1 IPFS Node** (distributed storage)
All containers use the `unless-stopped` restart policy for resilience.
---
## Container Architecture
```
┌─────────────────────────────────────────────────────────┐
│ Cloudflare Tunnel (DockFlare) │
└────────────────────┬────────────────────────────────────┘
┌────────────────┴────────────────────┐
│ net-public + cloudflare-net │
│ │
│ ┌──────────┐ ┌──────────┐ ┌──────────┐ ┌──────┐
│ │ sentry- │ │ sentry- │ │ sentry- │ │ IPFS │
│ │ alice │◄─► bob │◄─► carol │ │ │
│ └────┬─────┘ └────┬─────┘ └────┬─────┘ └──────┘
└───────┼─────────────┼─────────────┼─────────────────┘
│ │ │
│ private │ private │ private
│ │ │
┌───────▼──────┐ ┌────▼──────┐ ┌────▼──────┐
│ val-alice │ │ val-bob │ │ val-carol │
│ (net-alice) │ │ (net-bob) │ │(net-carol)│
└──────────────┘ └───────────┘ └───────────┘
```
---
## Validator Containers
Validators are the core consensus nodes that produce blocks and maintain blockchain state. They are isolated on private networks for security.
### val-alice
**Purpose:** Alice's validator node
**Image:** `onsonr/snrd:latest`
**Network:** `net-alice` (private)
**Volume:** `./val-alice:/root/.sonr`
**Configuration:**
- **Chain ID:** `sonrtest_1-1`
- **Moniker:** `val-alice`
- **Pruning:** Disabled (`--pruning=nothing`)
- **Min Gas Prices:** `0usnr` (free for testnet)
**Security Features:**
- Runs on isolated private network
- Only connects to its own sentry (`sentry-alice`)
- No direct public access
- Protected by sentry's `private_peer_ids` configuration
**Data Directory:**
```
./val-alice/
├── config/
│ ├── genesis.json # Genesis state
│ ├── config.toml # Tendermint config
│ ├── app.toml # Application config
│ └── priv_validator_key.json # Validator signing key (CRITICAL!)
└── data/ # Blockchain data
```
---
### val-bob
**Purpose:** Bob's validator node
**Image:** `onsonr/snrd:latest`
**Network:** `net-bob` (private)
**Volume:** `./val-bob:/root/.sonr`
**Configuration:**
- **Chain ID:** `sonrtest_1-1`
- **Moniker:** `val-bob`
- **Pruning:** Disabled
- **Min Gas Prices:** `0usnr`
**Security:** Same as val-alice, isolated on `net-bob`
---
### val-carol
**Purpose:** Carol's validator node
**Image:** `onsonr/snrd:latest`
**Network:** `net-carol` (private)
**Volume:** `./val-carol:/root/.sonr`
**Configuration:**
- **Chain ID:** `sonrtest_1-1`
- **Moniker:** `val-carol`
- **Pruning:** Disabled
- **Min Gas Prices:** `0usnr`
**Security:** Same as val-alice, isolated on `net-carol`
---
## Sentry Containers
Sentry nodes act as a protective layer between validators and the public internet. They handle all public RPC, REST, gRPC, and EVM requests while shielding validator identities.
### sentry-alice
**Purpose:** Alice's public-facing sentry node
**Image:** `onsonr/snrd:latest`
**Networks:**
- `net-alice` (connects to val-alice)
- `net-public` (connects to other sentries)
- `cloudflare-net` (for DockFlare tunnels)
**Volume:** `./sentry-alice:/root/.sonr`
**Depends On:** `val-alice`
**Configuration:**
- **Chain ID:** `sonrtest_1-1`
- **Moniker:** `sentry-alice`
- **Pruning:** Disabled
- **Min Gas Prices:** `0usnr`
**Exposed Services:**
- **RPC:** Port 26657 (Tendermint RPC)
- **REST:** Port 1317 (Cosmos REST API)
- **gRPC:** Port 9090 (gRPC endpoint)
- **EVM JSON-RPC:** Port 8545 (Ethereum-compatible)
- **EVM WebSocket:** Port 8546 (WebSocket subscriptions)
**JSON-RPC APIs Enabled:**
- `eth` - Ethereum JSON-RPC
- `txpool` - Transaction pool inspection
- `personal` - Account management
- `net` - Network info
- `debug` - Debugging APIs
- `web3` - Web3 utilities
**Cloudflare Tunnel Endpoints:**
| Endpoint | Hostname | Internal Service | Description |
|----------|----------|------------------|-------------|
| RPC | `alice-rpc.sonr.land` | `http://sentry-alice:26657` | Tendermint RPC for queries and transactions |
| REST | `alice-rest.sonr.land` | `http://sentry-alice:1317` | Cosmos REST API (LCD) |
| gRPC | `alice-grpc.sonr.land` | `http://sentry-alice:9090` | gRPC for efficient binary communication |
| EVM | `alice-evm.sonr.land` | `http://sentry-alice:8545` | EVM JSON-RPC (MetaMask compatible) |
**Peer Connections:**
- **Persistent Peer:** `val-alice` (private connection)
- **Seeds:** `sentry-bob`, `sentry-carol` (public P2P)
- **Private Peer IDs:** Marks `val-alice` as private to hide from network
**Security Features:**
- Shields validator from direct exposure
- Handles all public-facing traffic
- Rate limiting and DDoS protection via Cloudflare
- TLS encryption via Cloudflare tunnels
---
### sentry-bob
**Purpose:** Bob's public-facing sentry node
**Image:** `onsonr/snrd:latest`
**Networks:** `net-bob`, `net-public`, `cloudflare-net`
**Volume:** `./sentry-bob:/root/.sonr`
**Depends On:** `val-bob`
**Configuration:** Same as sentry-alice, with moniker `sentry-bob`
**Cloudflare Tunnel Endpoints:**
- `bob-rpc.sonr.land` → RPC (26657)
- `bob-rest.sonr.land` → REST (1317)
- `bob-grpc.sonr.land` → gRPC (9090)
- `bob-evm.sonr.land` → EVM JSON-RPC (8545)
**Peer Connections:**
- **Persistent Peer:** `val-bob`
- **Seeds:** `sentry-alice`, `sentry-carol`
---
### sentry-carol
**Purpose:** Carol's public-facing sentry node
**Image:** `onsonr/snrd:latest`
**Networks:** `net-carol`, `net-public`, `cloudflare-net`
**Volume:** `./sentry-carol:/root/.sonr`
**Depends On:** `val-carol`
**Configuration:** Same as sentry-alice, with moniker `sentry-carol`
**Cloudflare Tunnel Endpoints:**
- `carol-rpc.sonr.land` → RPC (26657)
- `carol-rest.sonr.land` → REST (1317)
- `carol-grpc.sonr.land` → gRPC (9090)
- `carol-evm.sonr.land` → EVM JSON-RPC (8545)
**Peer Connections:**
- **Persistent Peer:** `val-carol`
- **Seeds:** `sentry-alice`, `sentry-bob`
---
## IPFS Container
### ipfsctl
**Purpose:** Distributed file storage and content addressing
**Image:** `ipfs/kubo:latest` (official IPFS implementation)
**Networks:**
- `net-public` (connects to sentry nodes)
- `cloudflare-net` (for DockFlare tunnels)
**Volume:** `ipfs-data:/data/ipfs` (named volume)
**Configuration:**
- **IPFS Profile:** `server` (optimized for server deployment)
**Exposed Services:**
- **API:** Port 5001 (IPFS HTTP API)
- **Gateway:** Port 8080 (IPFS Gateway for content retrieval)
- **Swarm:** Port 4001 (P2P networking)
**Cloudflare Tunnel Endpoints:**
| Endpoint | Hostname | Internal Service | Description |
|----------|----------|------------------|-------------|
| API | `ipfs-api.sonr.land` | `http://ipfsctl:5001` | IPFS API for adding/pinning content |
| Gateway | `ipfs-gateway.sonr.land` | `http://ipfsctl:8080` | HTTP gateway for retrieving content |
**Features:**
- **Content-Addressed Storage:** Files identified by cryptographic hash (CID)
- **Distributed Network:** Connects to global IPFS network
- **Persistent Storage:** Data stored in named volume
- **HTTP API:** RESTful API for programmatic access
- **Gateway Access:** Retrieve content via HTTP using CID
**Common Operations:**
```bash
# Add file to IPFS
curl -X POST -F file=@myfile.txt https://ipfs-api.sonr.land/api/v0/add
# Retrieve file by CID
curl https://ipfs-gateway.sonr.land/ipfs/QmYwAPJzv5CZsnA625s3Xf2nemtYgPpHdWEz79ojWnPbdG/readme
# Check version
curl -X POST https://ipfs-api.sonr.land/api/v0/version | jq
```
---
## Network Topology
### Private Networks
Each validator has its own isolated network:
| Network | Purpose | Containers |
|---------|---------|------------|
| `net-alice` | Alice validator isolation | `val-alice`, `sentry-alice` |
| `net-bob` | Bob validator isolation | `val-bob`, `sentry-bob` |
| `net-carol` | Carol validator isolation | `val-carol`, `sentry-carol` |
**Security Benefits:**
- Validators cannot directly communicate with each other
- Prevents Byzantine attacks at network layer
- Forces all communication through sentries
### Public Network
| Network | Purpose | Containers |
|---------|---------|------------|
| `net-public` | Sentry interconnection | `sentry-alice`, `sentry-bob`, `sentry-carol`, `ipfsctl` |
**Purpose:**
- Sentries discover and connect to each other
- IPFS accessible to all sentries
- Public P2P gossip network
### Cloudflare Network
| Network | Purpose | Containers |
|---------|---------|------------|
| `cloudflare-net` | DockFlare tunnel access | `sentry-alice`, `sentry-bob`, `sentry-carol`, `ipfsctl` |
**Type:** External (must be created before starting stack)
**Purpose:** Allows DockFlare to discover and tunnel traffic to containers
**Setup:**
```bash
docker network create cloudflare-net
```
---
## Volume Management
### Bind Mounts (Validators & Sentries)
```
./val-alice:/root/.sonr
./val-bob:/root/.sonr
./val-carol:/root/.sonr
./sentry-alice:/root/.sonr
./sentry-bob:/root/.sonr
./sentry-carol:/root/.sonr
```
**Advantages:**
- Direct file system access from host
- Easy backup and inspection
- No permission issues (files owned by host user)
**Backup:**
```bash
tar -czf testnet-backup.tar.gz val-* sentry-*
```
### Named Volume (IPFS)
```
ipfs-data:/data/ipfs
```
**Advantages:**
- Managed by Docker
- Better performance on some systems
- Automatic cleanup with `docker compose down -v`
**Backup:**
```bash
docker run --rm -v ipfs-data:/data -v $(pwd):/backup alpine tar czf /backup/ipfs-backup.tar.gz /data
```
---
## Container Management
### Start All Containers
```bash
make start
# or
docker compose up -d
```
### Stop All Containers
```bash
make stop
# or
docker compose down
```
### View Container Logs
```bash
# All containers
docker compose logs -f
# Specific container
docker compose logs -f sentry-alice
# Last 100 lines
docker compose logs --tail=100 val-alice
```
### Execute Commands in Containers
```bash
# Via bootstrap script
devbox run exec sentry-alice status
# Via docker compose
docker compose exec sentry-alice snrd status --home /root/.sonr
# Via docker
docker exec -it sentry-alice snrd keys list --keyring-backend test
```
### Inspect Container Configuration
```bash
# View environment variables
docker inspect sentry-alice -f '{{json .Config.Env}}' | jq
# View networks
docker inspect sentry-alice -f '{{json .NetworkSettings.Networks}}' | jq
# View mounts
docker inspect sentry-alice -f '{{json .Mounts}}' | jq
```
### Resource Usage
```bash
# Real-time stats
docker stats
# Container resource limits (if set)
docker inspect sentry-alice -f '{{json .HostConfig.Memory}}' | jq
```
---
## Health Checks
### Container Status
```bash
docker ps --filter "name=val-" --filter "name=sentry-" --filter "name=ipfs"
```
### Node Sync Status
```bash
# Check if nodes are syncing
for container in sentry-alice sentry-bob sentry-carol; do
echo "=== $container ==="
docker exec $container sh -c 'curl -s http://localhost:26657/status | jq -r ".result.sync_info.catching_up"'
done
```
### Block Height
```bash
# Current block height
docker exec sentry-alice sh -c 'curl -s http://localhost:26657/status | jq -r ".result.sync_info.latest_block_height"'
```
### IPFS Health
```bash
# Check IPFS daemon
curl -X POST https://ipfs-api.sonr.land/api/v0/version | jq
# Check connected peers
curl -X POST https://ipfs-api.sonr.land/api/v0/swarm/peers | jq
```
---
## Security Considerations
### Validator Security
1. **Never expose validators directly** - Always use sentries
2. **Backup `priv_validator_key.json`** - Cannot be recovered if lost
3. **Monitor validator uptime** - Downtime results in slashing
4. **Use KMS in production** - Hardware security modules for key management
### Sentry Security
1. **Rate limiting via Cloudflare** - Protects against DDoS
2. **TLS encryption** - All traffic encrypted via Cloudflare tunnels
3. **No exposed ports** - All access via tunnels only
4. **Regular updates** - Keep `onsonr/snrd` image updated
### IPFS Security
1. **Content verification** - All content verified by CID
2. **No private data** - IPFS is a public network
3. **Pin important content** - Prevent garbage collection
4. **Monitor storage** - IPFS can grow large over time
---
## Troubleshooting
### Container Won't Start
```bash
# Check logs
docker compose logs <container-name>
# Check resource usage
docker stats
# Verify networks exist
docker network ls | grep -E "net-|cloudflare"
# Recreate container
docker compose up -d --force-recreate <container-name>
```
### Permission Issues
```bash
# Fix ownership (if needed)
sudo chown -R $USER:$USER val-* sentry-*
# Check bind mount permissions
ls -la val-alice/
```
### Network Connectivity Issues
```bash
# Test connectivity between containers
docker exec sentry-alice ping -c 3 val-alice
docker exec sentry-alice ping -c 3 sentry-bob
# Check network configuration
docker network inspect net-public
```
### IPFS Issues
```bash
# Check IPFS daemon status
docker compose logs ipfsctl
# Restart IPFS
docker compose restart ipfsctl
# Clear IPFS cache (WARNING: destructive)
docker compose down
docker volume rm testnet_ipfs-data
docker compose up -d
```
---
## Performance Tuning
### Resource Limits (Optional)
Add to `docker-compose.yml`:
```yaml
services:
val-alice:
deploy:
resources:
limits:
cpus: '2.0'
memory: 4G
reservations:
cpus: '1.0'
memory: 2G
```
### Logging Configuration
Prevent log bloat:
```yaml
services:
val-alice:
logging:
driver: "json-file"
options:
max-size: "100m"
max-file: "3"
```
---
## Maintenance
### Update Containers
```bash
# Pull latest images
docker compose pull
# Restart with new images
docker compose up -d
```
### Clean Up
```bash
# Remove stopped containers
docker compose down
# Remove all data (WARNING: destructive)
docker compose down -v
# Clean Docker system
docker system prune -a
```
### Backup Procedure
```bash
# Stop containers
make stop
# Backup data
tar -czf testnet-backup-$(date +%Y%m%d).tar.gz val-* sentry-* .env
# Backup IPFS volume
docker run --rm -v testnet_ipfs-data:/data -v $(pwd):/backup \
alpine tar czf /backup/ipfs-backup-$(date +%Y%m%d).tar.gz /data
# Restart containers
make start
```
+247
View File
@@ -0,0 +1,247 @@
# Environment Variables
This document describes all environment variables that can be configured for the Sonr testnet.
## Configuration File
All variables are defined in `.env` file in the repository root. Copy `.env.example` to `.env` and customize:
```bash
cp .env.example .env
```
---
## Global Configuration
These variables are used during initialization and apply to all services.
### Chain Configuration
| Variable | Default | Description |
|----------|---------|-------------|
| `CHAIN_ID` | `sonrtest_1-1` | Blockchain chain identifier |
| `DENOM` | `usnr` | Base denomination for the native token |
| `KEYRING` | `test` | Keyring backend (test, file, os) |
| `KEYALGO` | `eth_secp256k1` | Key algorithm for validator keys |
### Network Parameters
| Variable | Default | Description |
|----------|---------|-------------|
| `BLOCK_TIME` | `5s` | Target block time |
| `VOTING_PERIOD` | `30s` | Governance proposal voting period |
| `EXPEDITED_VOTING_PERIOD` | `15s` | Expedited proposal voting period |
| `MAX_GAS` | `100000000` | Maximum gas per block |
| `MIN_COMMISSION_RATE` | `0.050000000000000000` | Minimum validator commission rate (5%) |
### Validator Mnemonics
**⚠️ WARNING**: Change these for production! Default mnemonics are public.
| Variable | Description |
|----------|-------------|
| `ALICE_MNEMONIC` | 24-word mnemonic for Alice validator |
| `BOB_MNEMONIC` | 24-word mnemonic for Bob validator |
| `CAROL_MNEMONIC` | 24-word mnemonic for Carol validator |
| `FAUCET_MNEMONIC` | 24-word mnemonic for faucet account |
### Initial Balances
| Variable | Default | Description |
|----------|---------|-------------|
| `BASE_ALLOCATION` | `100000000000000000000000000usnr` | Base allocation per validator (100M SNR) |
| `STAKE_AMOUNT` | `30000000000000000000000usnr` | Initial stake per validator (30M SNR) |
| `FAUCET_ALLOCATION` | `250000000000000000000000000000usnr` | Faucet account balance (250M SNR) |
### Docker Configuration
| Variable | Default | Description |
|----------|---------|-------------|
| `DOCKER_IMAGE` | `onsonr/snrd:latest` | Docker image for validator and sentry nodes |
---
## Container-Specific Variables
These variables are set in `docker-compose.yml` for each container.
### Validators (val-alice, val-bob, val-carol)
All validators share the same environment variables but with different values:
| Variable | Value | Description |
|----------|-------|-------------|
| `CHAIN_ID` | `sonrtest_1-1` | Chain identifier (same for all) |
| `MONIKER` | `val-{name}` | Validator node name (val-alice, val-bob, val-carol) |
**Command-line flags:**
- `--home /root/.sonr` - Node home directory
- `--pruning=nothing` - Disable state pruning
- `--minimum-gas-prices=0usnr` - Minimum gas price (0 for testnet)
- `--chain-id=sonrtest_1-1` - Chain identifier
**Networks:**
- Private network: `net-{name}` (net-alice, net-bob, net-carol)
**Volumes:**
- `./val-{name}:/root/.sonr` - Bind mount for node data
---
### Sentries (sentry-alice, sentry-bob, sentry-carol)
All sentries share the same environment variables but with different values:
| Variable | Value | Description |
|----------|-------|-------------|
| `CHAIN_ID` | `sonrtest_1-1` | Chain identifier (same for all) |
| `MONIKER` | `sentry-{name}` | Sentry node name (sentry-alice, sentry-bob, sentry-carol) |
**Command-line flags:**
- `--home /root/.sonr` - Node home directory
- `--pruning=nothing` - Disable state pruning
- `--minimum-gas-prices=0usnr` - Minimum gas price (0 for testnet)
- `--rpc.laddr=tcp://0.0.0.0:26657` - RPC listen address
- `--json-rpc.api=eth,txpool,personal,net,debug,web3` - Enabled JSON-RPC APIs
- `--json-rpc.address=0.0.0.0:8545` - EVM JSON-RPC address
- `--json-rpc.ws-address=0.0.0.0:8546` - EVM WebSocket address
- `--chain-id=sonrtest_1-1` - Chain identifier
**Networks:**
- Private network: `net-{name}` (connects to validator)
- `net-public` (connects to other sentries)
- `cloudflare-net` (for DockFlare tunnels)
**Volumes:**
- `./sentry-{name}:/root/.sonr` - Bind mount for node data
**DockFlare Labels (indexed):**
Each sentry exposes 4 endpoints via Cloudflare tunnels:
| Index | Hostname Pattern | Service | Description |
|-------|------------------|---------|-------------|
| `0` | `{name}-rpc.sonr.land` | `http://sentry-{name}:26657` | Tendermint RPC |
| `1` | `{name}-rest.sonr.land` | `http://sentry-{name}:1317` | Cosmos REST API |
| `2` | `{name}-grpc.sonr.land` | `http://sentry-{name}:9090` | gRPC endpoint |
| `3` | `{name}-evm.sonr.land` | `http://sentry-{name}:8545` | EVM JSON-RPC |
**Example for sentry-alice:**
```yaml
labels:
- "dockflare.enable=true"
- "dockflare.0.hostname=alice-rpc.sonr.land"
- "dockflare.0.service=http://sentry-alice:26657"
- "dockflare.1.hostname=alice-rest.sonr.land"
- "dockflare.1.service=http://sentry-alice:1317"
- "dockflare.2.hostname=alice-grpc.sonr.land"
- "dockflare.2.service=http://sentry-alice:9090"
- "dockflare.3.hostname=alice-evm.sonr.land"
- "dockflare.3.service=http://sentry-alice:8545"
```
---
### IPFS (ipfsctl)
| Variable | Value | Description |
|----------|-------|-------------|
| `IPFS_PROFILE` | `server` | IPFS configuration profile for server mode |
**Networks:**
- `net-public` (connects to sentries)
- `cloudflare-net` (for DockFlare tunnels)
**Volumes:**
- `ipfs-data:/data/ipfs` - Named volume for IPFS data
**DockFlare Labels:**
| Index | Hostname | Service | Description |
|-------|----------|---------|-------------|
| `0` | `ipfs-api.sonr.land` | `http://ipfsctl:5001` | IPFS API endpoint |
| `1` | `ipfs-gateway.sonr.land` | `http://ipfsctl:8080` | IPFS Gateway |
---
## DockFlare Configuration
DockFlare requires the following environment variables (not in `.env`, set when running DockFlare container):
| Variable | Required | Description |
|----------|----------|-------------|
| `CLOUDFLARE_API_TOKEN` | ✅ Yes | Cloudflare API token with Tunnel:Edit, DNS:Edit, Zone:Read permissions |
| `CLOUDFLARE_ACCOUNT_ID` | ⚠️ Recommended | Cloudflare account ID (found in dashboard) |
| `CLOUDFLARE_ZONE_ID` | ⚠️ Recommended | Cloudflare zone ID for domain (found in dashboard) |
**Example DockFlare Setup:**
```bash
docker run -d \
--name dockflare \
--restart unless-stopped \
--network cloudflare-net \
-v /var/run/docker.sock:/var/run/docker.sock \
-e CLOUDFLARE_API_TOKEN=your_token_here \
-e CLOUDFLARE_ACCOUNT_ID=your_account_id \
-e CLOUDFLARE_ZONE_ID=your_zone_id \
ghcr.io/sonr-io/dockflare:latest
```
---
## Runtime Overrides
You can override specific values at runtime by modifying `docker-compose.yml` or passing environment variables:
### Override Docker Image
```bash
export DOCKER_IMAGE=onsonr/snrd:v1.2.3
make start
```
### Override Chain ID
Edit `docker-compose.yml` and change all instances of:
```yaml
environment:
- CHAIN_ID=your-custom-chain-id
```
And update command flags:
```yaml
command: >
snrd start
...
--chain-id=your-custom-chain-id
```
---
## Security Best Practices
1. **Never commit `.env` to version control** - It's already in `.gitignore`
2. **Generate new mnemonics for production**:
```bash
snrd keys add test --keyring-backend test --output json | jq -r .mnemonic
```
3. **Use KMS for production validator keys** (e.g., tmkms)
4. **Rotate Cloudflare API tokens** regularly
5. **Use strong passwords** if switching from `test` keyring to `file` or `os`
6. **Backup mnemonics securely** - They cannot be recovered if lost
---
## Verification
After configuration, verify your setup:
```bash
# Check .env is loaded
make status
# Test endpoints
make test
# View container environment
docker inspect sentry-alice -f '{{json .Config.Env}}' | jq
```
+66
View File
@@ -0,0 +1,66 @@
# Sonr Testnet Makefile
.PHONY: help all init start stop restart clean status logs test setup
# Default target
.DEFAULT_GOAL := help
# Help target
help:
@echo "Sonr Testnet Management (via Devbox)"
@echo ""
@echo "Setup:"
@echo " make all - Check/install devbox"
@echo ""
@echo "Testnet Operations:"
@echo " make setup - Create .env from template"
@echo " make init - Initialize validators and sentries"
@echo " make start - Start testnet"
@echo " make stop - Stop testnet"
@echo " make restart - Restart testnet"
@echo " make clean - Clean all data"
@echo " make status - Show status"
@echo " make logs - View logs"
@echo ""
@echo "Testing:"
@echo " make test - Run basic tests"
# Check/install devbox
all:
@command -v devbox >/dev/null 2>&1 || (echo "Installing devbox..." && curl -fsSL https://get.jetpack.io/devbox | bash)
@echo "✅ devbox is ready"
# Setup .env file
setup:
@devbox run setup
# Initialize validators
init:
@devbox run init
# Start testnet
start:
@devbox run start
# Stop testnet
stop:
@devbox run stop
# Restart testnet
restart:
@devbox run restart
# Clean all data
clean:
@devbox run clean
# Show status
status:
@devbox run status
# View logs
logs:
@devbox run logs
# Run tests
test:
@devbox run test
+407
View File
@@ -0,0 +1,407 @@
# Sonr Testnet
Production-ready 3-validator testnet with validator-sentry architecture and Cloudflare tunnel integration via DockFlare.
## Overview
This testnet provides:
- **3 Validators** with isolated private networks
- **3 Sentry Nodes** for public access and DDoS protection
- **IPFS Node** for distributed storage
- **Cloudflare Tunnels** for secure, zero-configuration public endpoints
- **14 Public Endpoints** via `*.sonr.land` domains
## Quick Start
### Prerequisites
1. **Docker & Docker Compose**
```bash
docker --version
docker compose version
```
2. **Devbox** (provides snrd binary via Nix)
```bash
# Auto-install via Makefile
make all
# Or install manually
curl -fsSL https://get.jetpack.io/devbox | bash
```
3. **DockFlare** (for Cloudflare tunnels)
```bash
docker network create cloudflare-net
docker run -d \
--name dockflare \
--restart unless-stopped \
--network cloudflare-net \
-v /var/run/docker.sock:/var/run/docker.sock \
-e CLOUDFLARE_API_TOKEN=your_token_here \
-e CLOUDFLARE_ACCOUNT_ID=your_account_id \
-e CLOUDFLARE_ZONE_ID=your_zone_id \
ghcr.io/sonr-io/dockflare:latest
```
> Get credentials from: https://dash.cloudflare.com
### Setup
```bash
# 1. Clone repository
git clone https://github.com/sonr-io/testnet
cd testnet
# 2. Install devbox (if not already installed)
make all
# 3. Create environment configuration
make setup
# Optional: Edit .env to customize
# 4. Initialize testnet
make init
# 5. Start testnet
make start
# 6. Verify endpoints
make test
```
**That's it!** Your testnet is running with Cloudflare tunnels.
---
## Commands
All testnet operations are managed via `make`:
```bash
make all # Check/install devbox
make setup # Create .env from template
make init # Initialize validators and sentries
make start # Start testnet
make stop # Stop testnet
make restart # Restart testnet
make clean # Clean all data (WARNING: destructive)
make status # Show status and endpoints
make logs # View logs
make test # Run basic tests
make help # Show available commands
```
> **Note:** All commands use devbox under the hood, which provides the `snrd` binary via Nix.
---
## Public Endpoints
All services are accessible via Cloudflare tunnels (no port conflicts):
### Sentry Endpoints
**Alice:**
- RPC: `https://alice-rpc.sonr.land`
- REST: `https://alice-rest.sonr.land`
- gRPC: `https://alice-grpc.sonr.land`
- EVM: `https://alice-evm.sonr.land`
**Bob:**
- RPC: `https://bob-rpc.sonr.land`
- REST: `https://bob-rest.sonr.land`
- gRPC: `https://bob-grpc.sonr.land`
- EVM: `https://bob-evm.sonr.land`
**Carol:**
- RPC: `https://carol-rpc.sonr.land`
- REST: `https://carol-rest.sonr.land`
- gRPC: `https://carol-grpc.sonr.land`
- EVM: `https://carol-evm.sonr.land`
### IPFS Endpoints
- API: `https://ipfs-api.sonr.land`
- Gateway: `https://ipfs-gateway.sonr.land`
### Example Usage
```bash
# Query blockchain status
curl https://alice-rpc.sonr.land/status | jq
# Query account balance
curl https://alice-rest.sonr.land/cosmos/bank/v1beta1/balances/idx16wx7ye3ce060tjvmmpu8lm0ak5xr7gm2vjyh4k | jq
# Send transaction
snrd tx bank send alice idx1... 1000000usnr \
--node https://alice-rpc.sonr.land \
--chain-id sonrtest_1-1 \
--keyring-backend test \
--yes
# IPFS operations
curl -X POST https://ipfs-api.sonr.land/api/v0/version | jq
curl https://ipfs-gateway.sonr.land/ipfs/<CID>
```
---
## Architecture
```
Cloudflare Tunnel (DockFlare)
┌──────────────────────────────────────────────┐
│ net-public + cloudflare-net │
│ │
│ ┌──────────────┐ ┌──────────────┐ ┌──────────────┐ ┌──────────┐
│ │sentry-alice │◄─►sentry-bob │◄─►sentry-carol │ │ IPFS │
│ └──────┬───────┘ └──────┬───────┘ └──────┬───────┘ └──────────┘
└─────────┼──────────────────┼──────────────────┼──────────────────────┘
│ │ │
│ Private │ Private │ Private
│ │ │
┌─────────▼────────┐ ┌──────▼────────┐ ┌─────▼─────────┐
│ val-alice │ │ val-bob │ │ val-carol │
│ (net-alice) │ │ (net-bob) │ │ (net-carol) │
└──────────────────┘ └───────────────┘ └───────────────┘
```
### Key Features
- **Validator Isolation**: Each validator on private network
- **Sentry Protection**: Public traffic filtered through sentries
- **No Port Conflicts**: All services via Cloudflare tunnels
- **Auto-Discovery**: DockFlare automatically creates tunnels
- **TLS Encryption**: All traffic encrypted via Cloudflare
---
## Genesis Accounts
| Name | Address | Balance | Purpose |
|------|---------|---------|---------|
| Alice | `idx140fehngcrxvhdt84x729p3f0qmkmea8n570lrg` | 100M SNR | Validator |
| Bob | `idx1r6yue0vuyj9m7xw78npspt9drq2tmtvgcrf7sr` | 100M SNR | Validator |
| Carol | `idx1pe9mc2q72u94sn2gg52ramrt26x5efw6kslflg` | 100M SNR | Validator |
| Faucet | `idx16wx7ye3ce060tjvmmpu8lm0ak5xr7gm2vjyh4k` | 250M SNR | Faucet |
**Total Genesis Supply:** 550M SNR (300M staked + 250M faucet)
---
## Configuration
Configuration is managed via `.env` file:
```bash
cp .env.example .env
```
Quick setup:
```bash
make setup # Creates .env from .env.example
```
**Key Variables:**
- `CHAIN_ID=sonrtest_1-1` - Chain identifier
- `DENOM=usnr` - Native token denomination
- `BLOCK_TIME=5s` - Target block time
- `VOTING_PERIOD=30s` - Governance voting period
- `ALICE_MNEMONIC`, `BOB_MNEMONIC`, `CAROL_MNEMONIC` - Validator keys
- `FAUCET_MNEMONIC` - Faucet account key
- `DOCKER_IMAGE=onsonr/snrd:latest` - Container image
**⚠️ WARNING:** Default mnemonics in `.env.example` are public. Generate new ones for production!
For complete configuration details, see [docs/Environment.md](docs/Environment.md)
---
## Documentation
### Detailed Guides
- **[Docker.md](docs/Docker.md)** - Complete container documentation
- All 7 containers explained
- Network topology and security
- Volume management
- Health checks and troubleshooting
- Performance tuning
- Backup procedures
- **[Cloudflare.md](docs/Cloudflare.md)** - DockFlare integration guide
- Complete domain mapping (14 endpoints)
- DockFlare setup and configuration
- DNS management
- Testing all endpoint types
- Access policies
- Troubleshooting tunnels
- **[Environment.md](docs/Environment.md)** - Environment variable reference
- Global configuration variables
- Container-specific variables
- DockFlare environment variables
- Runtime overrides
- Security best practices
- **[Architecture.md](docs/Architecture.md)** - Architecture deep dive
- **[CLAUDE.md](CLAUDE.md)** - Quick reference for AI assistants
---
## Troubleshooting
### Initialization Takes 1-2 Minutes
This is normal. The script initializes 6 nodes, creates genesis, and configures peer connections.
**Expected output:**
- 📋 Initializing validators
- 🛡️ Initializing sentries
- 💰 Adding genesis accounts
- 🔗 Setting up peer connections
- ✅ Completion with validator addresses
**If init fails:**
```bash
make clean
make init
```
### Validators Not Syncing
```bash
# Check logs
docker compose logs val-alice
# Verify peer connections
docker exec val-alice snrd tendermint show-node-id --home /root/.sonr
```
### Cloudflare Tunnels Not Working
Check DockFlare logs:
```bash
docker logs dockflare
```
Common issues:
- Missing `cloudflare-net` network
- Invalid API token
- Container not on `cloudflare-net`
See [docs/Cloudflare.md#troubleshooting](docs/Cloudflare.md#troubleshooting) for detailed help.
### IPFS Port Conflict
If IPFS fails with "port 8080 already allocated":
1. Stop the conflicting service
2. Or modify `docker-compose.yml` to use different port
---
## Production Deployment
**Before deploying to production:**
1. ✅ **Generate new mnemonics** - Never use defaults
```bash
snrd keys add test --keyring-backend test --output json | jq -r .mnemonic
```
2. ✅ **Use KMS** for validator key management (e.g., tmkms)
3. ✅ **Configure firewall rules** to restrict validator access
4. ✅ **Enable monitoring** (Prometheus, Grafana)
5. ✅ **Set up backups** of validator keys and state
```bash
tar -czf backup.tar.gz val-* sentry-* .env
```
6. ✅ **Rotate Cloudflare API tokens** regularly (every 90 days)
7. ✅ **Enable rate limiting** in Cloudflare dashboard
8. ✅ **Use persistent volumes** instead of bind mounts (optional)
---
## Development
### View Logs
```bash
# All services
make logs
# Specific service
docker compose logs -f sentry-alice
# Search logs
docker compose logs val-alice | grep -i error
```
### Execute Commands
```bash
# Via docker compose (recommended)
docker compose exec sentry-alice snrd query bank total
# Direct docker exec
docker exec -it sentry-alice snrd keys list --keyring-backend test
```
### Clean Restart
```bash
make clean # Remove all data (destructive!)
make init # Reinitialize
make start # Start fresh
```
---
## Testing
```bash
# Run basic tests
make test
```
### Manual Testing
```bash
# RPC
curl https://alice-rpc.sonr.land/status | jq
# REST
curl https://alice-rest.sonr.land/cosmos/base/tendermint/v1beta1/node_info | jq
# EVM JSON-RPC
curl -X POST https://alice-evm.sonr.land \
-H "Content-Type: application/json" \
-d '{"jsonrpc":"2.0","method":"eth_chainId","params":[],"id":1}' | jq
# IPFS
curl -X POST https://ipfs-api.sonr.land/api/v0/version | jq
```
---
## Support
- **Documentation**: See [docs/](docs/) directory
- **Issues**: https://github.com/sonr-io/testnet/issues
- **Discord**: https://discord.gg/sonr
---
## License
Apache 2.0
+200
View File
@@ -0,0 +1,200 @@
name: sonr-testnet
networks:
net-naruto:
net-senku:
net-yaeger:
net-public:
dokploy-network:
external: true
services:
val-naruto:
image: onsonr/snrd:latest
container_name: val-naruto
command: sh -c "mkdir -p /root/.sonr && /usr/bin/testnet-setup.sh && snrd start --home /root/.sonr --pruning=nothing --minimum-gas-prices=0usnr --chain-id=sonrtest_1-1"
environment:
- CHAIN_ID=sonrtest_1-1
- MONIKER=val-naruto
- NODE_TYPE=validator
- VALIDATOR_NAME=val-naruto
- WAIT_FOR_SYNC=false
volumes:
- ../val-naruto:/root/.sonr
networks:
- net-naruto
restart: unless-stopped
sentry-naruto:
image: onsonr/snrd:latest
container_name: sentry-naruto
command: sh -c "/usr/bin/testnet-setup.sh && snrd start --home /root/.sonr --pruning=nothing --minimum-gas-prices=0usnr --rpc.laddr=tcp://0.0.0.0:26657 --json-rpc.api=eth,txpool,personal,net,debug,web3 --json-rpc.address=0.0.0.0:8545 --json-rpc.ws-address=0.0.0.0:8546 --chain-id=sonrtest_1-1"
environment:
- CHAIN_ID=sonrtest_1-1
- MONIKER=sentry-naruto
- NODE_TYPE=sentry
- VALIDATOR_NAME=sentry-naruto
- WAIT_FOR_SYNC=true
volumes:
- ../sentry-naruto:/root/.sonr
networks:
- net-naruto
- net-public
- dokploy-network
labels:
- traefik.enable=true
- traefik.http.routers.naruto-rpc.rule=Host(`${naruto_rpc_domain}`)
- traefik.http.routers.naruto-rpc.entrypoints=websecure
- traefik.http.routers.naruto-rpc.tls.certResolver=letsencrypt
- traefik.http.services.naruto-rpc.loadbalancer.server.port=26657
- traefik.http.routers.naruto-rest.rule=Host(`${naruto_rest_domain}`)
- traefik.http.routers.naruto-rest.entrypoints=websecure
- traefik.http.routers.naruto-rest.tls.certResolver=letsencrypt
- traefik.http.services.naruto-rest.loadbalancer.server.port=1317
- traefik.http.routers.naruto-grpc.rule=Host(`${naruto_grpc_domain}`)
- traefik.http.routers.naruto-grpc.entrypoints=websecure
- traefik.http.routers.naruto-grpc.tls.certResolver=letsencrypt
- traefik.http.services.naruto-grpc.loadbalancer.server.port=9090
- traefik.http.routers.naruto-evm.rule=Host(`${naruto_evm_domain}`)
- traefik.http.routers.naruto-evm.entrypoints=websecure
- traefik.http.routers.naruto-evm.tls.certResolver=letsencrypt
- traefik.http.services.naruto-evm.loadbalancer.server.port=8545
depends_on:
- val-naruto
restart: unless-stopped
# Senku's Validator
val-senku:
image: onsonr/snrd:latest
container_name: val-senku
command: sh -c "/usr/bin/testnet-setup.sh && snrd start --home /root/.sonr --pruning=nothing --minimum-gas-prices=0usnr --chain-id=sonrtest_1-1"
environment:
- CHAIN_ID=sonrtest_1-1
- MONIKER=val-senku
- NODE_TYPE=validator
- VALIDATOR_NAME=val-senku
- WAIT_FOR_SYNC=false
volumes:
- ../val-senku:/root/.sonr
networks:
- net-senku
restart: unless-stopped
# Senku's Sentry
sentry-senku:
image: onsonr/snrd:latest
container_name: sentry-senku
command: sh -c "/usr/bin/testnet-setup.sh && snrd start --home /root/.sonr --pruning=nothing --minimum-gas-prices=0usnr --rpc.laddr=tcp://0.0.0.0:26657 --json-rpc.api=eth,txpool,personal,net,debug,web3 --json-rpc.address=0.0.0.0:8545 --json-rpc.ws-address=0.0.0.0:8546 --chain-id=sonrtest_1-1"
environment:
- CHAIN_ID=sonrtest_1-1
- MONIKER=sentry-senku
- NODE_TYPE=sentry
- VALIDATOR_NAME=sentry-senku
- WAIT_FOR_SYNC=true
volumes:
- ../sentry-senku:/root/.sonr
networks:
- net-senku
- net-public
- dokploy-network
labels:
- traefik.enable=true
- traefik.http.routers.senku-rpc.rule=Host(`${senku_rpc_domain}`)
- traefik.http.routers.senku-rpc.entrypoints=websecure
- traefik.http.routers.senku-rpc.tls.certResolver=letsencrypt
- traefik.http.services.senku-rpc.loadbalancer.server.port=26657
- traefik.http.routers.senku-rest.rule=Host(`${senku_rest_domain}`)
- traefik.http.routers.senku-rest.entrypoints=websecure
- traefik.http.routers.senku-rest.tls.certResolver=letsencrypt
- traefik.http.services.senku-rest.loadbalancer.server.port=1317
- traefik.http.routers.senku-grpc.rule=Host(`${senku_grpc_domain}`)
- traefik.http.routers.senku-grpc.entrypoints=websecure
- traefik.http.routers.senku-grpc.tls.certResolver=letsencrypt
- traefik.http.services.senku-grpc.loadbalancer.server.port=9090
- traefik.http.routers.senku-evm.rule=Host(`${senku_evm_domain}`)
- traefik.http.routers.senku-evm.entrypoints=websecure
- traefik.http.routers.senku-evm.tls.certResolver=letsencrypt
- traefik.http.services.senku-evm.loadbalancer.server.port=8545
depends_on:
- val-senku
restart: unless-stopped
# Yaeger's Validator
val-yaeger:
image: onsonr/snrd:latest
container_name: val-yaeger
command: sh -c "/usr/bin/testnet-setup.sh && snrd start --home /root/.sonr --pruning=nothing --minimum-gas-prices=0usnr --chain-id=sonrtest_1-1"
environment:
- CHAIN_ID=sonrtest_1-1
- MONIKER=val-yaeger
- NODE_TYPE=validator
- VALIDATOR_NAME=val-yaeger
- WAIT_FOR_SYNC=false
volumes:
- ../val-yaeger:/root/.sonr
networks:
- net-yaeger
restart: unless-stopped
# Yaeger's Sentry (Public Node)
sentry-yaeger:
image: onsonr/snrd:latest
container_name: sentry-yaeger
command: sh -c "/usr/bin/testnet-setup.sh && snrd start --home /root/.sonr --pruning=nothing --minimum-gas-prices=0usnr --rpc.laddr=tcp://0.0.0.0:26657 --json-rpc.api=eth,txpool,personal,net,debug,web3 --json-rpc.address=0.0.0.0:8545 --json-rpc.ws-address=0.0.0.0:8546 --chain-id=sonrtest_1-1"
environment:
- CHAIN_ID=sonrtest_1-1
- MONIKER=sentry-yaeger
- NODE_TYPE=sentry
- VALIDATOR_NAME=sentry-yaeger
- WAIT_FOR_SYNC=true
volumes:
- ../sentry-yaeger:/root/.sonr
networks:
- net-yaeger
- net-public
- dokploy-network
labels:
- traefik.enable=true
- traefik.http.routers.yaeger-rpc.rule=Host(`${yaeger_rpc_domain}`)
- traefik.http.routers.yaeger-rpc.entrypoints=websecure
- traefik.http.routers.yaeger-rpc.tls.certResolver=letsencrypt
- traefik.http.services.yaeger-rpc.loadbalancer.server.port=26657
- traefik.http.routers.yaeger-rest.rule=Host(`${yaeger_rest_domain}`)
- traefik.http.routers.yaeger-rest.entrypoints=websecure
- traefik.http.routers.yaeger-rest.tls.certResolver=letsencrypt
- traefik.http.services.yaeger-rest.loadbalancer.server.port=1317
- traefik.http.routers.yaeger-grpc.rule=Host(`${yaeger_grpc_domain}`)
- traefik.http.routers.yaeger-grpc.entrypoints=websecure
- traefik.http.routers.yaeger-grpc.tls.certResolver=letsencrypt
- traefik.http.services.yaeger-grpc.loadbalancer.server.port=9090
- traefik.http.routers.yaeger-evm.rule=Host(`${yaeger_evm_domain}`)
- traefik.http.routers.yaeger-evm.entrypoints=websecure
- traefik.http.routers.yaeger-evm.tls.certResolver=letsencrypt
- traefik.http.services.yaeger-evm.loadbalancer.server.port=8545
depends_on:
- val-yaeger
restart: unless-stopped
ipfsctl:
image: ipfs/kubo:latest
container_name: ipfsctl
environment:
- IPFS_PROFILE=server
volumes:
- ipfs-data:/data/ipfs
networks:
- net-public
- dokploy-network
labels:
- traefik.enable=true
- traefik.http.routers.ipfs-api.rule=Host(`${ipfs_api_domain}`)
- traefik.http.routers.ipfs-api.entrypoints=websecure
- traefik.http.routers.ipfs-api.tls.certResolver=letsencrypt
- traefik.http.services.ipfs-api.loadbalancer.server.port=5001
- traefik.http.routers.ipfs-gateway.rule=Host(`${ipfs_gateway_domain}`)
- traefik.http.routers.ipfs-gateway.entrypoints=websecure
- traefik.http.routers.ipfs-gateway.tls.certResolver=letsencrypt
- traefik.http.services.ipfs-gateway.loadbalancer.server.port=8080
restart: unless-stopped
volumes:
ipfs-data:
+107
View File
@@ -0,0 +1,107 @@
[variables]
# Naruto Sentry Domains
naruto_rpc_domain = "${domain}"
naruto_rest_domain = "${domain}"
naruto_grpc_domain = "${domain}"
naruto_evm_domain = "${domain}"
# Senku Sentry Domains
senku_rpc_domain = "${domain}"
senku_rest_domain = "${domain}"
senku_grpc_domain = "${domain}"
senku_evm_domain = "${domain}"
# Yaeger Sentry Domains
yaeger_rpc_domain = "${domain}"
yaeger_rest_domain = "${domain}"
yaeger_grpc_domain = "${domain}"
yaeger_evm_domain = "${domain}"
# IPFS Domains
ipfs_api_domain = "${domain}"
ipfs_gateway_domain = "${domain}"
[config]
# Naruto Sentry RPC
[[config.domains]]
serviceName = "sentry-naruto"
port = 26657
host = "${naruto_rpc_domain}"
# Naruto Sentry REST
[[config.domains]]
serviceName = "sentry-naruto"
port = 1317
host = "${naruto_rest_domain}"
# Naruto Sentry gRPC
[[config.domains]]
serviceName = "sentry-naruto"
port = 9090
host = "${naruto_grpc_domain}"
# Naruto Sentry EVM
[[config.domains]]
serviceName = "sentry-naruto"
port = 8545
host = "${naruto_evm_domain}"
# Senku Sentry RPC
[[config.domains]]
serviceName = "sentry-senku"
port = 26657
host = "${senku_rpc_domain}"
# Senku Sentry REST
[[config.domains]]
serviceName = "sentry-senku"
port = 1317
host = "${senku_rest_domain}"
# Senku Sentry gRPC
[[config.domains]]
serviceName = "sentry-senku"
port = 9090
host = "${senku_grpc_domain}"
# Senku Sentry EVM
[[config.domains]]
serviceName = "sentry-senku"
port = 8545
host = "${senku_evm_domain}"
# Yaeger Sentry RPC
[[config.domains]]
serviceName = "sentry-yaeger"
port = 26657
host = "${yaeger_rpc_domain}"
# Yaeger Sentry REST
[[config.domains]]
serviceName = "sentry-yaeger"
port = 1317
host = "${yaeger_rest_domain}"
# Yaeger Sentry gRPC
[[config.domains]]
serviceName = "sentry-yaeger"
port = 9090
host = "${yaeger_grpc_domain}"
# Yaeger Sentry EVM
[[config.domains]]
serviceName = "sentry-yaeger"
port = 8545
host = "${yaeger_evm_domain}"
# IPFS API
[[config.domains]]
serviceName = "ipfsctl"
port = 5001
host = "${ipfs_api_domain}"
# IPFS Gateway
[[config.domains]]
serviceName = "ipfsctl"
port = 8080
host = "${ipfs_gateway_domain}"