Skip to content

Commit 5afa8d5

Browse files
committed
Update ECS deployment documentation
1 parent 95b2fc5 commit 5afa8d5

File tree

1 file changed

+110
-38
lines changed

1 file changed

+110
-38
lines changed

deployments/ecs/ecs-instruction.md

Lines changed: 110 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,7 @@ Each ECS task runs a single mpcium node with:
4646
│ │ │ │ │ │ │ │ │ │
4747
│ │ │ init-secrets │ │ init-secrets │ │ init-secrets │ │ │
4848
│ │ │ init-config │ │ init-config │ │ init-config │ │ │
49+
│ │ │ init-data │ │ init-data │ │ init-data │ │ │
4950
│ │ │ mpcium │ │ mpcium │ │ mpcium │ │ │
5051
│ │ │ ▼ EFS │ │ ▼ EFS │ │ ▼ EFS │ │ │
5152
│ │ └──────┬───────┘ └──────┬───────┘ └──────┬───────┘ │ │
@@ -71,11 +72,12 @@ Each ECS task runs a single mpcium node with:
7172

7273
### Task Structure
7374

74-
Each ECS task contains three containers:
75+
Each ECS task contains four containers:
7576

7677
1. **init-secrets** — Pulls passwords from AWS Secrets Manager, writes to `/secrets/` volume
7778
2. **init-config** — Downloads config.yaml, peers.json, and identity files from S3
78-
3. **mpcium** — Main application container (distroless, no shell)
79+
3. **init-data** — Copies identity files and peers.json from ephemeral volumes to EFS (`/app/data/`) so they persist across restarts
80+
4. **mpcium** — Main application container (distroless, no shell)
7981

8082
## Pre-Deployment Setup
8183

@@ -251,6 +253,12 @@ Secrets Manager S3
251253
│ → /secrets/ │ │ → /config/ │
252254
│ │ │ → /identity/ │
253255
└──────┬───────┘ └──────┬───────┘
256+
│ │
257+
│ ┌──────┴───────┐
258+
│ │ init-data │
259+
│ │ copies to EFS │
260+
│ │ /app/data/ │
261+
│ └──────┬────────┘
254262
│ shared volumes │
255263
└──────────┬─────────────┘
256264
@@ -265,6 +273,8 @@ Secrets Manager S3
265273

266274
The main container is distroless (no shell), so all secrets must be pre-written to files by the init containers.
267275

276+
**NATS and Consul connection strings** are injected via environment variables (`NATS_URL`, `CONSUL_ADDRESS`) on the mpcium container rather than hardcoded in `config.yaml`. The config file should leave these fields empty — the application reads env vars as overrides at runtime.
277+
268278
## Task Definition Reference
269279

270280
Template task definition for a single mpcium node. Replace all `<PLACEHOLDER>` values.
@@ -278,8 +288,10 @@ Template task definition for a single mpcium node. Replace all `<PLACEHOLDER>` v
278288
| `<S3_BUCKET>` | S3 bucket for config files |
279289
| `<EFS_FILE_SYSTEM_ID>` | EFS file system ID |
280290
| `<EFS_ACCESS_POINT_ID>` | EFS access point ID for this node |
281-
| `<SECRETS_MANAGER_DB_PASSWORD_ARN>` | Secrets Manager secret name for BadgerDB password |
282-
| `<SECRETS_MANAGER_IDENTITY_PASSWORD_ARN>` | Secrets Manager secret name for identity password |
291+
| `<SECRETS_MANAGER_DB_PASSWORD_ARN>` | Secrets Manager secret ARN for BadgerDB password |
292+
| `<SECRETS_MANAGER_IDENTITY_PASSWORD_ARN>` | Secrets Manager secret ARN for identity password |
293+
| `<NATS_URL>` | NATS connection URL (e.g., `nats://nlb.internal:4222`) |
294+
| `<CONSUL_ADDRESS>` | Consul address with port (e.g., `nlb.internal:8500`) |
283295

284296
```json
285297
{
@@ -297,7 +309,7 @@ Template task definition for a single mpcium node. Replace all `<PLACEHOLDER>` v
297309
"essential": false,
298310
"entryPoint": ["sh", "-c"],
299311
"command": [
300-
"aws secretsmanager get-secret-value --secret-id <SECRETS_MANAGER_DB_PASSWORD_ARN> --query SecretString --output text > /secrets/mpcium-db-password.cred && aws secretsmanager get-secret-value --secret-id <SECRETS_MANAGER_IDENTITY_PASSWORD_ARN> --query SecretString --output text > /secrets/mpcium-identity-password.cred && chmod 400 /secrets/*.cred"
312+
"aws secretsmanager get-secret-value --secret-id <SECRETS_MANAGER_DB_PASSWORD_ARN> --query SecretString --output text > /secrets/mpcium-db-password.cred && aws secretsmanager get-secret-value --secret-id <SECRETS_MANAGER_IDENTITY_PASSWORD_ARN> --query SecretString --output text > /secrets/mpcium-identity-password.cred && chmod 444 /secrets/*.cred"
301313
],
302314
"mountPoints": [
303315
{
@@ -320,7 +332,7 @@ Template task definition for a single mpcium node. Replace all `<PLACEHOLDER>` v
320332
"essential": false,
321333
"entryPoint": ["sh", "-c"],
322334
"command": [
323-
"aws s3 cp s3://<S3_BUCKET>/mpcium/<NODE_NAME>/config.yaml /config/config.yaml && aws s3 cp s3://<S3_BUCKET>/mpcium/peers.json /config/peers.json && aws s3 cp s3://<S3_BUCKET>/mpcium/<NODE_NAME>/identity/ /identity/ --recursive && chmod 400 /identity/*.age && chmod 444 /identity/*.json /config/config.yaml /config/peers.json"
335+
"aws s3 cp s3://<S3_BUCKET>/mpcium/<NODE_NAME>/config.yaml /config/config.yaml && aws s3 cp s3://<S3_BUCKET>/mpcium/peers.json /config/peers.json && aws s3 cp s3://<S3_BUCKET>/mpcium/<NODE_NAME>/identity/ /identity/ --recursive && chmod 444 /identity/*.age /identity/*.json /config/config.yaml /config/peers.json"
324336
],
325337
"mountPoints": [
326338
{
@@ -347,6 +359,44 @@ Template task definition for a single mpcium node. Replace all `<PLACEHOLDER>` v
347359
}
348360
}
349361
},
362+
{
363+
"name": "init-data",
364+
"image": "amazon/aws-cli:latest",
365+
"essential": false,
366+
"entryPoint": ["sh", "-c"],
367+
"command": [
368+
"rm -f /app/data/peers.json && rm -rf /app/data/identity && cp -r /identity /app/data/identity && cp /config/peers.json /app/data/peers.json"
369+
],
370+
"mountPoints": [
371+
{
372+
"sourceVolume": "config",
373+
"containerPath": "/config"
374+
},
375+
{
376+
"sourceVolume": "identity",
377+
"containerPath": "/identity"
378+
},
379+
{
380+
"sourceVolume": "data",
381+
"containerPath": "/app/data"
382+
}
383+
],
384+
"dependsOn": [
385+
{
386+
"containerName": "init-config",
387+
"condition": "SUCCESS"
388+
}
389+
],
390+
"user": "65532:65532",
391+
"logConfiguration": {
392+
"logDriver": "awslogs",
393+
"options": {
394+
"awslogs-group": "/ecs/mpcium",
395+
"awslogs-region": "<AWS_REGION>",
396+
"awslogs-stream-prefix": "init-data"
397+
}
398+
}
399+
},
350400
{
351401
"name": "mpcium",
352402
"image": "<AWS_ACCOUNT_ID>.dkr.ecr.<AWS_REGION>.amazonaws.com/mpcium:<IMAGE_TAG>",
@@ -360,10 +410,14 @@ Template task definition for a single mpcium node. Replace all `<PLACEHOLDER>` v
360410
"--decrypt-private-key",
361411
"--peers=/config/peers.json"
362412
],
363-
"portMappings": [
413+
"environment": [
364414
{
365-
"containerPort": 8080,
366-
"protocol": "tcp"
415+
"name": "NATS_URL",
416+
"value": "<NATS_URL>"
417+
},
418+
{
419+
"name": "CONSUL_ADDRESS",
420+
"value": "<CONSUL_ADDRESS>"
367421
}
368422
],
369423
"mountPoints": [
@@ -397,13 +451,6 @@ Template task definition for a single mpcium node. Replace all `<PLACEHOLDER>` v
397451
"condition": "SUCCESS"
398452
}
399453
],
400-
"healthCheck": {
401-
"command": ["CMD-SHELL", "wget -q --spider http://localhost:8080/health || exit 1"],
402-
"interval": 30,
403-
"timeout": 5,
404-
"retries": 3,
405-
"startPeriod": 60
406-
},
407454
"linuxParameters": {
408455
"initProcessEnabled": true
409456
},
@@ -416,8 +463,7 @@ Template task definition for a single mpcium node. Replace all `<PLACEHOLDER>` v
416463
"awslogs-region": "<AWS_REGION>",
417464
"awslogs-stream-prefix": "mpcium"
418465
}
419-
},
420-
"stopTimeout": 10
466+
}
421467
}
422468
],
423469
"volumes": [
@@ -459,14 +505,16 @@ Template task definition for a single mpcium node. Replace all `<PLACEHOLDER>` v
459505
}
460506
```
461507

508+
> **Note**: The `NATS_URL` and `CONSUL_ADDRESS` environment variables override the corresponding fields in `config.yaml`. This allows the same config file to be used across environments — only the ECS task definition env vars need to change.
509+
462510
### Volume Mount Summary
463511

464-
| Volume | Init-secrets | Init-config | Mpcium (main) | Persistent |
465-
|--------|:---:|:---:|:---:|:---:|
466-
| `secrets` (`/secrets/``/app/secrets/`) | write | - | read-only | No (ephemeral) |
467-
| `config` (`/config/`) | - | write | read-only | No (ephemeral) |
468-
| `identity` (`/identity/``/app/identity/`) | - | write | read-only | No (ephemeral) |
469-
| `data` (`/app/data/`) | - | - | read-write | Yes (EFS) |
512+
| Volume | Init-secrets | Init-config | Init-data | Mpcium (main) | Persistent |
513+
|--------|:---:|:---:|:---:|:---:|:---:|
514+
| `secrets` (`/secrets/``/app/secrets/`) | write | - | - | read-only | No (ephemeral) |
515+
| `config` (`/config/`) | - | write | read | read-only | No (ephemeral) |
516+
| `identity` (`/identity/``/app/identity/`) | - | write | read | read-only | No (ephemeral) |
517+
| `data` (`/app/data/`) | - | - | write | read-write | Yes (EFS) |
470518

471519
### Runtime File Paths (per node)
472520

@@ -486,7 +534,13 @@ EFS directory structure per node's access point:
486534
/ (EFS access point root = /<NODE_NAME> on the filesystem)
487535
├── db/
488536
│ └── <NODE_NAME>/ ← BadgerDB encrypted data
489-
└── backups/ ← encrypted .enc backup files
537+
├── backups/ ← encrypted .enc backup files
538+
├── identity/ ← copied from S3 by init-data container
539+
│ ├── node0_identity.json
540+
│ ├── node0_private.key.age
541+
│ ├── node1_identity.json
542+
│ └── node2_identity.json
543+
└── peers.json ← copied from S3 by init-data container
490544
```
491545

492546
## IAM Policies Reference
@@ -565,29 +619,37 @@ db_path: /app/data/db
565619
backup_dir: /app/data/backups
566620

567621
# Consul service discovery
622+
# Leave empty when using CONSUL_ADDRESS env var override in ECS task definition
568623
consul:
569-
address: <CONSUL_ADDRESS>:8500
624+
address: ""
570625

571-
# NATS messaging (TLS required in production)
626+
# NATS messaging
627+
# Leave empty when using NATS_URL env var override in ECS task definition
628+
# For production with TLS, uncomment the tls block and upload certs to S3
572629
nats:
573-
url: nats://<NATS_ADDRESS>:4222
574-
username: <NATS_USERNAME>
575-
password: <NATS_PASSWORD>
576-
tls:
577-
client_cert: /config/certs/client-cert.pem
578-
client_key: /config/certs/client-key.pem
579-
ca_cert: /config/certs/rootCA.pem
630+
url: ""
631+
# username: <NATS_USERNAME>
632+
# password: <NATS_PASSWORD>
633+
# tls:
634+
# client_cert: /config/certs/client-cert.pem
635+
# client_key: /config/certs/client-key.pem
636+
# ca_cert: /config/certs/rootCA.pem
580637

581638
# MPC threshold (t-of-n, where t >= floor(n/2) + 1)
582639
mpc_threshold: 2
583640

584-
# Event initiator public key (Ed25519 hex)
641+
# Event initiator public key (hex encoded)
585642
event_initiator_pubkey: <EVENT_INITIATOR_PUBKEY>
586-
event_initiator_algorithm: ed25519
643+
# Algorithm: "ed25519" or "p256"
644+
event_initiator_algorithm: <ALGORITHM>
587645

588646
# Chain code (32-byte hex, 64 characters)
589647
chain_code: <CHAIN_CODE_HEX>
590648

649+
# Concurrency limits
650+
max_concurrent_keygen: 3
651+
max_concurrent_signing: 10
652+
591653
# Backup settings
592654
# Application-level: writes encrypted .enc files to backup_dir for granular recovery.
593655
# Volume-level: enable AWS Backup on the EFS file system for full snapshots.
@@ -614,7 +676,17 @@ After tasks start, the mpcium container logs should show (in order):
614676

615677
### Health Check
616678

617-
The task definition health check hits `GET /health` on port 8080. Tasks should report `HEALTHY` within 60 seconds of starting (configured via `startPeriod`).
679+
The application exposes `GET /health` on port 8080 (configured via `healthcheck.address` in config.yaml). The current deployment does not define an ECS-level container health check — the application health endpoint is available for use by load balancers or external monitoring. If you need ECS to track container health, add a `healthCheck` block to the mpcium container definition:
680+
681+
```json
682+
"healthCheck": {
683+
"command": ["CMD-SHELL", "wget -q --spider http://localhost:8080/health || exit 1"],
684+
"interval": 30,
685+
"timeout": 5,
686+
"retries": 3,
687+
"startPeriod": 60
688+
}
689+
```
618690

619691
### Functional Test
620692

@@ -686,5 +758,5 @@ See https://github.com/fystack/mpcium-client-ts.
686758
---
687759

688760
**Version**: 0.3.3
689-
**Last Updated**: March 2, 2026
761+
**Last Updated**: March 26, 2026
690762
**Maintainer**: FyStack Team

0 commit comments

Comments
 (0)