vta-service 0.4.0

Service for Verifiable Trust Agents operating in Verifiable Trust Communities
Documentation

vta-service

Verifiable Trust Agent (VTA) service for the First Person Network. A VTA manages cryptographic keys, DID-based authentication, DIDComm messaging, and access control policies for a Verifiable Trust Community.

Quick Start

# Build (includes setup wizard and OS keyring by default)
cargo build --package vta-service

# Run the interactive setup wizard
vta setup

# Start the server
vta

# Start with a custom config file
vta --config /path/to/config.toml

The setup wizard walks through DID creation, mediator configuration, seed storage backend selection, and admin credential generation.

CLI Reference

vta [OPTIONS] [COMMAND]

Running vta with no subcommand starts the server.

Global options:

Flag Description
-c, --config <PATH> Path to configuration file (default: config.toml or $VTA_CONFIG_PATH)

Subcommands:

Command Description
setup Run the interactive setup wizard (requires setup feature)
export-admin Export admin DID and credential bundle
status Show VTA status and statistics
create-did-key Create a did:key in a context (offline)
create-did-webvh Create a did:webvh DID for a context (requires setup feature)
import-did Import an external DID and create an ACL entry (offline)
acl Manage Access Control List entries (offline)
keys Manage keys (offline)

create-did-key

vta create-did-key --context <ID> [--admin] [--label <LABEL>]
Flag Description
--context <ID> Target context ID (required)
--admin Also create an ACL entry with Admin role
--label <LABEL> Human-readable label for the key record and ACL entry

create-did-webvh

vta create-did-webvh --context <ID> [--label <LABEL>]
Flag Description
--context <ID> Target context ID (required)
--label <LABEL> Label prefix for key records (defaults to context ID)

import-did

vta import-did --did <DID> [--role <ROLE>] [--label <LABEL>] [--context <CTX>...]
Flag Description
--did <DID> The DID to import (required)
--role <ROLE> Role to assign: admin, initiator, or application
--label <LABEL> Human-readable label for the ACL entry
--context <CTX> Restrict to specific context(s); repeatable. Omit for unrestricted access

acl

vta acl <SUBCOMMAND>
Subcommand Description
list [--context <CTX>] [--role <ROLE>] List all ACL entries, optionally filtered
get <DID> Show details of a single ACL entry
update <DID> [--role <ROLE>] [--label <LABEL>] [--contexts <CTX,...>] Update an existing ACL entry
delete <DID> [-y] Delete an ACL entry (-y to skip confirmation)

keys

vta keys <SUBCOMMAND>
Subcommand Description
list [--context <CTX>] [--status <STATUS>] List keys (filter by context or status: active/revoked)
secrets [KEY_IDS...] [--context <CTX>] Export secret key material for specified keys or all active keys in a context
seeds List seed generations and their status
rotate-seed [--mnemonic <WORDS>] Rotate to a new master seed (generates random if mnemonic omitted)

HTTP API

All routes except /health and /auth/* require a valid JWT bearer token (Authorization: Bearer <token>).

Health

Method Path Description
GET /health Health check

Authentication

Method Path Description
POST /auth/challenge Request a DID-based auth challenge
POST /auth/ Authenticate with a signed challenge response
POST /auth/refresh Refresh an access token
POST /auth/credentials Generate credentials
GET /auth/sessions List active sessions
DELETE /auth/sessions Revoke all sessions for a DID
DELETE /auth/sessions/{session_id} Revoke a specific session

Keys

Method Path Description
GET /keys List keys
POST /keys Create a new key
GET /keys/{key_id} Get key details
PATCH /keys/{key_id} Rename a key
DELETE /keys/{key_id} Invalidate (revoke) a key
GET /keys/{key_id}/secret Export secret key material
GET /keys/seeds List seed generations
POST /keys/seeds/rotate Rotate to a new master seed

Contexts

Method Path Description
GET /contexts List contexts
POST /contexts Create a context
GET /contexts/{id} Get context details
PATCH /contexts/{id} Update a context
DELETE /contexts/{id} Delete a context

Access Control

Method Path Description
GET /acl List ACL entries
POST /acl Create an ACL entry
GET /acl/{did} Get an ACL entry
PATCH /acl/{did} Update an ACL entry
DELETE /acl/{did} Delete an ACL entry

Configuration

Method Path Description
GET /config Get current configuration
PATCH /config Update configuration

Backup & Restore

Method Path Description
POST /backup/export Export encrypted backup (Admin)
POST /backup/import Import encrypted backup (Admin)

VTA Management

Method Path Description
POST /vta/restart Trigger soft restart (Admin)

Configuration

Configuration is loaded from a TOML file (default: config.toml). Every field can be overridden with an environment variable.

Top-level

TOML Field Env Var Description
vta_did VTA_DID The VTA's own DID
vta_name Human-readable name (alias: community_name)
public_url VTA_PUBLIC_URL Public-facing URL of this VTA instance

[services]

TOML Field Default Description
rest true Enable the REST API thread
didcomm true Enable the DIDComm messaging thread

At least one service must be enabled. These can also be disabled at compile time via the rest and didcomm Cargo features.

[server]

TOML Field Env Var Default Description
host VTA_SERVER_HOST 0.0.0.0 Bind address
port VTA_SERVER_PORT 8100 Bind port

[log]

TOML Field Env Var Default Description
level VTA_LOG_LEVEL info Log level (also: RUST_LOG)
format VTA_LOG_FORMAT text text or json

[store]

TOML Field Env Var Default Description
data_dir VTA_STORE_DATA_DIR data/vta Path to the fjall KV store data directory

[messaging]

TOML Field Env Var Description
mediator_url VTA_MESSAGING_MEDIATOR_URL DIDComm mediator endpoint URL
mediator_did VTA_MESSAGING_MEDIATOR_DID DIDComm mediator DID

[auth]

TOML Field Env Var Default Description
access_token_expiry VTA_AUTH_ACCESS_EXPIRY 900 Access token lifetime in seconds
refresh_token_expiry VTA_AUTH_REFRESH_EXPIRY 86400 Refresh token lifetime in seconds
challenge_ttl VTA_AUTH_CHALLENGE_TTL 300 Auth challenge TTL in seconds
session_cleanup_interval VTA_AUTH_SESSION_CLEANUP_INTERVAL 600 Expired session cleanup interval in seconds
jwt_signing_key VTA_AUTH_JWT_SIGNING_KEY Base64url-encoded 32-byte Ed25519 private key for JWT signing

[secrets]

TOML Field Env Var Default Description
seed VTA_SECRETS_SEED Hex-encoded BIP-32 seed (config-seed feature)
aws_secret_name VTA_SECRETS_AWS_SECRET_NAME AWS Secrets Manager secret name
aws_region VTA_SECRETS_AWS_REGION AWS region override
gcp_project VTA_SECRETS_GCP_PROJECT GCP project ID
gcp_secret_name VTA_SECRETS_GCP_SECRET_NAME GCP secret name
azure_vault_url VTA_SECRETS_AZURE_VAULT_URL Azure Key Vault URL
azure_secret_name VTA_SECRETS_AZURE_SECRET_NAME Azure Key Vault secret name
keyring_service VTA_SECRETS_KEYRING_SERVICE vta OS keyring service name

Cargo Features

Feature Default Description
setup Yes Interactive setup wizard and did:webvh creation
keyring Yes OS keyring seed storage backend
rest Yes REST API thread (module and thread spawning)
didcomm Yes DIDComm messaging thread (module and thread spawning)
config-seed No Store BIP-32 seed as hex in the TOML config file
aws-secrets No AWS Secrets Manager seed storage backend
gcp-secrets No Google Cloud Secret Manager seed storage backend
azure-secrets No Azure Key Vault seed storage backend

A plaintext file fallback (seed.plaintext in the data directory) is always available regardless of feature flags.

Architecture

The server runs up to three dedicated OS threads, each with its own single-threaded Tokio runtime. The REST and DIDComm threads are conditional — they only start when enabled by both the [services] config and their corresponding Cargo feature flag.

  1. REST thread (vta-rest) — Serves the Axum HTTP API. Requires the rest feature and services.rest = true.

  2. DIDComm thread (vta-didcomm) — Connects to the configured mediator and processes inbound DIDComm messages. Requires the didcomm feature and services.didcomm = true. Stays idle if vta_did or messaging is not configured.

  3. Storage thread (vta-storage) — Always runs. Handles periodic session cleanup and persists the fjall KV store on shutdown. Guarantees all writes are flushed before the database closes.

At least one of REST or DIDComm must be enabled or the server will refuse to start. Shutdown is coordinated via a watch channel — SIGINT or SIGTERM triggers graceful shutdown of all threads.

Key Modules

Module Description
server AppState, thread orchestration, auth initialization
routes Axum router and HTTP handler modules
config TOML config loading with env var overrides
keys BIP-32 key derivation, key records, seed management
auth DID challenge-response auth, JWT tokens, sessions
messaging DIDComm mediator connection and message loop
store fjall KV store wrapper with keyspace handles
acl Access control list management
contexts Context CRUD operations

Seed Storage Backends

The BIP-32 master seed can be stored in any of the following backends. The seed store is selected based on which [secrets] fields are configured (checked in order):

Backend Feature Config Fields
AWS Secrets Manager aws-secrets aws_secret_name (+ optional aws_region)
GCP Secret Manager gcp-secrets gcp_project + gcp_secret_name
Azure Key Vault azure-secrets azure_vault_url + azure_secret_name
Config file (hex) config-seed seed
OS keyring keyring keyring_service
Plaintext file — (always available) Falls back to seed.plaintext in data_dir

License

Apache-2.0