Get ECCA Running Locally

Clone the repo, spin up all 24 services with Docker Compose, deploy contracts, and test every endpoint — in under 10 minutes.

Prerequisites

Node.js ≥ 20.10

nodejs.org

📦

pnpm ≥ 9.7

npm i -g pnpm

🐳

Docker + Compose v2

docker.com

🔧

Git

git-scm.com

Optional: Go 1.22+ is only needed if you want to build the chain forks from source. Docker handles this automatically.

1 — Clone & Install

1

Clone the repository

git clone https://github.com/aarong11/dhf.git
cd dhf
2

Install all dependencies

pnpm install

This installs all packages, services, and workers across the monorepo via pnpm workspaces.

3

Build the TypeScript packages

pnpm build

Turborepo builds everything in dependency order: proto → crypto → bus → db → chain → service-base → services → workers


2 — Environment Configuration

Copy the example environment file and customize if needed:

cp .env.example .env
Defaults work out of the box. The .env.example ships with working values for local Docker development. You only need to edit it if you want to use OpenAI/Anthropic instead of Ollama, or change ports.

Key Environment Variables

VariableDefaultPurpose
DATABASE_URLpostgresql://ecca:quellcrist@...PostgreSQL connection
NATS_URLnats://axonal-bus:4222Event bus (JetStream)
REDIS_URLredis://working-memory-cache:6379Ephemeral cache
CORTEX_RPChttp://cortex-evm:8545EVM chain RPC
MEDULLA_RPChttp://medulla-pow:8332PoW chain RPC
HIPPOCAMPUS_APIhttp://hippocampus-dag:5001DAG storage API
ECCA_EPOCH_INTERVAL_MS4000Epoch tick interval
ECCA_DRIFT_MAX15Max drift before desync
ECCA_FIDELITY_MIN0.6Minimum recall fidelity
SIYANA_PORT7070Main API port
LLM_PROVIDERollamaollama | openai | anthropic

3 — Start All Services

1

Build and launch all 24 services

pnpm compose:up

This runs docker compose up -d --build. First build takes 3-5 minutes; subsequent starts are faster.

2

Watch the logs (optional)

pnpm compose:logs
3

Verify services are healthy

# Check all containers are running
docker compose ps

# Health checks
curl http://localhost:7070/healthz       # Siyana API
curl http://localhost:8332/health        # Medulla PoW
curl http://localhost:15001/health       # Hippocampus DAG

4 — Deploy Smart Contracts

Once Cortex EVM is running on port 8545, deploy the 7 Solidity contracts:

pnpm contracts:deploy

This deploys StackIdentity, BandwidthToken, QuellistTreasury, ResidueRegistry, SleeveRegistry, EpochAnchor, and NeedlecastRouter to the local Cortex EVM chain. Contract addresses are written to deployments/cortex.json.


5 — Verify Everything Works

# Run the test suite
pnpm test

# Or run the full end-to-end demo
pnpm demo

🧪 Run Tests in Your Browser

Test every endpoint end-to-end with live request/response output, blockchain verification, and log guidance — no tools to install.

▶ Open Test Runner

Demo Flow

The demo script exercises the full cognitive cycle:

01
Create Stack
02
Spawn Sleeves
03
Perceive ×5
04
Sync
05
Recall
06
Needlecast
07
Epoch Tick
08
Balances

Run the Demo

pnpm demo

This creates a Stack, spawns human + AI sleeves, writes 5 perceptions, syncs, recalls with fidelity check, needlecasts between sleeves, triggers an epoch, and prints token balances + residues.


API Testing

Two ways to test every endpoint against your local Docker services:

🧪

Browser Test Runner

Run all 25 tests end-to-end right here. See requests, responses, blockchain state, and where to check logs — zero install required.

📮

Postman Collection

30 requests with test scripts. Import into Postman desktop or web.

↓ Download .json

How to Import

1

Open Postman

Use the desktop app or web.postman.co (browser version).

2

Import → Upload Files

Click Import in the top-left, select the downloaded .json file.

3

Run requests in order

Start with Create StackSpawn SleeveDrip Faucet → then test perceive, recall, needlecast. Variables auto-populate from responses.

Browser Note: If using Postman Web, you'll need the Postman Desktop Agent installed to send requests to localhost.

Siyana API

:7070

The main gateway. All client requests go through Siyana.

Stack Management

POST /v1/stacks

Create a new identity stack. Returns the stack ID, token ID, public key, and initial balances.

// Request
{ "name": "quellcrist-01", "kind": "autonomous" }

// Response
{ "id": "stk_...", "tokenId": 1, "name": "quellcrist-01",
  "kind": "autonomous", "pubKey": "0xabc...", "epoch": 0,
  "cpv": { "compute": 0.5, "memory": 0.3, "sync": 0.15, "routing": 0.05 },
  "binding": "cortex-mainnet" }
GET /v1/stacks

List all stacks with their sleeves.

GET /v1/stacks/:id

Get a single stack with sleeves and anchor history.

Sleeve Lifecycle

POST /v1/sleeves

Spawn a new sleeve (embodiment) attached to a stack.

// Request
{ "stackId": "stk_...", "embodimentType": "human", "hostname": "local-01" }

// Response
{ "id": "slv_...", "stackId": "stk_...", "embodimentType": "human",
  "alive": true, "drift": 0, "syncEpoch": 0,
  "tokens": { "compute": 1000, "memory": 1000, "sync": 500, "routing": 500 } }
GET /v1/sleeves

List all alive sleeves.

DELETE /v1/sleeves/:id

Decommission a sleeve. Marks it as not alive.

Perceive & Recall

POST /v1/sleeves/:id/perceive

Write a perception to memory. Costs 0.5 compute tokens and increments drift by 1.

// Request
{ "input": "The sunset cast long shadows across the rooftops of Harlan's World." }

// Response
{ "cid": "bafk...", "thought": "perception stored" }
GET /v1/stacks/:id/recall

Reconstruct memory from the DAG. Traverses depth levels and decrypts fragments.

// Query params: ?depth=6&memoryToken=1000

// Response
{ "fragments": ["decrypted memory text...", ...],
  "broken": [],
  "fidelity": 0.95 }
POST /v1/sleeves/:id/sync

Sync a sleeve to the current epoch. Resets drift to 0, costs 1 sync token.

Needlecasting

POST /v1/needlecast

Transfer consciousness from one sleeve to another (re-sleeving). Runs a 6-step atomic saga.

// Request
{ "from": "slv_source", "to": "slv_target" }

// Response (delegated to needlecast-router-svc)
{ "ok": true, "sagaId": "saga_...", "route": [...], "shards": [...] }

Coordination & Epochs

GET /v1/epochs/current

Get the current epoch number, block height, and chain tip.

POST /v1/mining/block

Trigger a Proof-of-Work block on Medulla. Returns the block hash and new epoch.

GET /v1/coordination/desync

List all sleeves with drift exceeding the threshold (default: 15).

GET /v1/coordination/residues

Get the last 50 coordination residues (errors as economic objects).

Tokens

GET /v1/tokens/balances/:stackId

Get aggregated token balances across all alive sleeves for a stack.

Bandwidth Faucet

:7075

Rate-limited token dispenser for development. Grants 100 of each token type per drip, with a 60-second cooldown.

POST /v1/faucet/drip

Request free tokens. Rate-limited to once per 60 seconds per stack.

// Request
{ "stackId": "stk_..." }

// Response
{ "ok": true, "granted": { "compute": 100, "memory": 100, "sync": 100, "routing": 100 },
  "sleeves": ["slv_..."] }

Thalamus Router

:7072

Epoch tick engine. Folds all chain roots into a single coherence root each epoch.

GET /v1/epoch

Get the current epoch number.

POST /v1/epoch/tick

Force an epoch fold. Computes the coherence root from EVM, IPFS, and sleeve Merkle roots and anchors it to Medulla.

DHF Compositor

:7073

Memory reconstruction engine. Walks the DAG and decrypts fragments using epoch keys.

POST /v1/reconstruct

Reconstruct memory for a stack. Decrypts all DAG nodes within the given depth.

// Request
{ "stackId": "stk_...", "sleeveId": "slv_...", "depth": 6 }

// Response
{ "ok": true, "fragments": ["memory text...", ...],
  "broken": [], "fidelity": 0.92 }

Needlecast Router

:7071

Atomic re-sleeving saga. Handles the 6-step consciousness transfer between sleeves.

POST /needlecast

Initiate needlecast transfer. Runs: freeze → snapshot → shard → transmit → reassemble → activate.

// Request
{ "from": "slv_source", "to": "slv_target" }

// Response
{ "ok": true, "sagaId": "saga_...",
  "route": ["freeze","snapshot","shard","transmit","reassemble","activate"],
  "shards": ["shard_1", "shard_2", "shard_3"] }

Quellist Treasury

:7074

Token emission engine. Issues bandwidth tokens based on the CPV curve and epoch delta.

GET /v1/treasury/issuance/:stackId

Get the last 100 emission events for a stack.

POST /v1/treasury/claim

Claim pending token emissions for a stack.

// Request
{ "stackId": "stk_..." }

// Response
{ "stackId": "stk_...", "claimable": { "compute": 50, "memory": 30, "sync": 15, "routing": 5 } }

Sleeve Runtime

:varies

4-in-1 parametric embodiment. Each sleeve instance exposes its own identity endpoint.

GET /identity

Returns the sleeve's identity, kind, parent stack, and hostname.

// Response
{ "sleeveId": "slv_...", "kind": "human",
  "stackId": "stk_...", "hostname": "local-01" }

Port Map

ServicePortProtocolNotes
Siyana API7070HTTP + WSMain gateway
Needlecast Router7071HTTPInternal
Thalamus Router7072HTTPInternal
DHF Compositor7073HTTPInternal
Quellist Treasury7074HTTPInternal
Bandwidth Faucet7075HTTPPublic
Cortex EVM8545JSON-RPCEthereum-compatible
Medulla PoW8332HTTPCustom PoW chain
Hippocampus DAG15001HTTPContent-addressed store
PostgreSQL5432TCPMain database
Redis6380TCPCache (mapped 6380→6379)
NATS4222TCPEvent bus
MinIO9000HTTPS3-compatible object store
Grafana3030HTTPDashboards
Prometheus9090HTTPMetrics
Jaeger16686HTTPTraces

Infrastructure Services

These are started automatically by Docker Compose and don't need manual setup:

  • PostgreSQL — Stack/sleeve/epoch registry (ecca_registry database)
  • Redis — Ephemeral working memory cache
  • NATS JetStream — Axonal event bus for inter-service communication
  • MinIO — S3-compatible shard storage for Hippocampus

Observability

Full observability stack is included:

  • Grafana — Dashboards at :3030 (admin/admin)
  • Prometheus — Metrics at :9090
  • Jaeger — Distributed traces at :16686
  • Loki — Log aggregation at :3100

Common Issues

FIX Port already in use

Another process is using a required port. Stop it or change the port in .env.

# Find what's using port 7070
lsof -i :7070        # macOS/Linux
netstat -ano | findstr :7070  # Windows
FIX Database connection refused

PostgreSQL may not be ready yet. Wait a few seconds or check the container:

docker compose logs cortical-registry-db
FIX Contracts deploy fails

Make sure Cortex EVM is fully initialized before deploying. The geth init + mining takes ~10 seconds.

# Check cortex is ready
curl http://localhost:8545 -X POST -H "Content-Type: application/json" \
  -d '{"jsonrpc":"2.0","method":"eth_blockNumber","params":[],"id":1}'
FIX Full reset

Nuclear option — tear down everything and start fresh:

pnpm compose:down   # removes containers + volumes
pnpm compose:up     # rebuild from scratch

Reading Logs

# All services
pnpm compose:logs

# Single service
docker compose logs -f siyana-api

# Last 50 lines of a service
docker compose logs --tail 50 thalamus-router