Skip to content

Latest commit

 

History

History
553 lines (458 loc) · 31.3 KB

File metadata and controls

553 lines (458 loc) · 31.3 KB

AgenticNetOS Agentic-Nets — Open-Source Repository

Overview

This is the public, open-source part of AgenticNetOS — the Agentic Workflow OS. It contains the open-source services, deployment configurations, and monitoring stack.

Closed-source core services (node, master, gui) are distributed as pre-built Docker Hub images and governed by PROPRIETARY-EULA.md. All source code in this repo is licensed under LICENSE.md (BSL 1.1).

Changelog rotation

CHANGELOG.md at the repo root holds only the current calendar quarter's releases. Older quarters live under changelogs/ — see changelogs/README.md for the rotation rule and quarterly archive index. The full convention is documented in the workspace root ../CLAUDE.md under "Release Notes". Do not rename or move CHANGELOG.md — Jenkins prepare-release reads it by exact path.

Repository Structure

agentic-nets/
├── LICENSE.md                         # BSL 1.1 (open-source code)
├── PROPRIETARY-EULA.md                # EULA for Docker Hub images (node, master, gui)
├── README.md
├── .gitignore
├── .dockerignore
│
├── agentic-net-gateway/                  # OAuth2 API gateway (Spring Boot, Java 21)
├── agentic-net-executor/                 # Command executor (Spring Boot, Java 21)
├── agentic-net-vault/                    # Secrets management via OpenBao (Spring Boot, Java 21)
├── agentic-net-cli/                      # CLI tool (TypeScript, Node.js 22)
├── agentic-net-chat/                     # Telegram bot (TypeScript, Node.js 22)
├── agentic-net-mcp/                      # MCP server (TypeScript, Node.js 22)
├── sa-blobstore/                      # Blob storage (Spring Boot, Java 21)
│
├── deployment/
│   ├── docker-compose.yml             # Hybrid: Hub images (closed) + local builds (open)
│   ├── docker-compose.hub-only.yml    # All services from Docker Hub
│   ├── .env.template                  # Environment config template (no secrets)
│   ├── dockerfiles/
│   │   ├── Dockerfile.agentic-net-gateway
│   │   ├── Dockerfile.agentic-net-executor
│   │   ├── Dockerfile.agentic-net-cli
│   │   ├── Dockerfile.agentic-net-chat
│   │   ├── Dockerfile.agentic-net-vault
│   │   └── Dockerfile.sa-blobstore
│   └── scripts/
│       └── build-and-push.sh          # Build & push open-source images only
│
└── monitoring/
    ├── config/
    │   ├── otel-collector-config.yaml
    │   ├── prometheus.yaml
    │   └── tempo.yaml
    └── grafana-provisioning/
        ├── dashboards/
        └── datasources/

Services

agentic-net-gateway (Port 8083)

Purpose: OAuth2 API gateway for secure distributed access.

  • Technology: Spring Boot 3.5.5, Spring Security with JWT
  • Routes: Master (/api/... — model-aware, multi-master registry), Node (/node-api/...), Vault (/vault-api/...)
  • Auth: JWT-based with auto-token acquisition. THREE OAuth2 clients, secrets auto-generated to data/jwt/: agenticos-admin (full access), agenticos-readonly (reads only), agenticos-executor (scope-enforced to the executor polling protocol only: poll/discover/deployment/tokens emit-consume-release — anything else returns 403 executor_scope). Pin via AGENTICOS_ADMIN_SECRET / AGENTICOS_READONLY_SECRET / AGENTICOS_EXECUTOR_SECRET.
  • Internal service auth (2.59): set AGENTICOS_SERVICE_TOKEN (all services) and node/master/vault/ blobstore require X-Service-Auth: Bearer <token> on their APIs (health stays open; blob GET-by-id stays open); the gateway proxies, master's node/vault/blob clients, the executor and node's backup sink send it. The Desktop launcher sets it automatically from its per-install internal secret. Unset = open (legacy).
  • Executor identity: executors mint tokens with executor_id; the JWT carries executorId, the gateway pins poll/discover to it and stamps X-Agenticos-Executor-Id for master, which refuses deployment/consume/ release for another executor's reservations. Pin a specific executor to its own secret with AGENTICOS_EXECUTOR_SECRET_<ID> (or <jwt-key-dir>/executor-<id>-secret).
  • Readonly scope never reaches /vault-api/**, the executor protocol (poll/discover/credentials/ tokens), the universal assistant or any non-domain-expert-readonly agent-stream, on any method.
  • Multi-master: masters self-register (POST /internal/masters/register + heartbeat, shared GATEWAY_INTERNAL_SECRET); routing by modelId, discover/executors fan out. Heartbeat for an unknown master returns 404 so the master re-registers after a gateway restart. Blank MASTER_URL disables the seed master. See agentic-net-gateway/ARCHITECTURE-MULTI-MASTER.md.
  • Key role: Enables executor, CLI, and chat to reach master/node across network boundaries
  • Build: cd agentic-net-gateway && ./mvnw clean package -DskipTests

agentic-net-executor (Port 8084)

Purpose: Distributed command execution service. Executes shell commands on behalf of command-type transitions.

  • Technology: Spring Boot 3.5.5, Java 21
  • Execution: ProcessBuilder("bash", "-c", command), supports exec and script modes
  • Multi-model: Composite modelId:transitionId keys, discovers models via master API
  • Build: cd agentic-net-executor && ./mvnw clean package -DskipTests

Dual Polling Mode

The executor uses egress-only polling — it reaches out to fetch work, never receives inbound connections:

Mode When Polls Auth
Gateway (compose default) Everywhere; required for remote executors and multi-master http://agentic-net-gateway:8083 OAuth2 client-credentials JWT (agenticos-executor client, auto re-fetched ~60s before expiry)
Direct Same trusted network as master, single master http://agentic-net-master:8082 None (internal)
# Gateway mode (default in all compose files)
EXECUTOR_UPSTREAM_URL=http://agentic-net-gateway:8083
EXECUTOR_AUTH_CLIENT_ID=agenticos-executor
# secret: either inline...
EXECUTOR_AUTH_CLIENT_SECRET=<value of AGENTICOS_EXECUTOR_SECRET>
# ...or lazily read from the gateway-generated file (mounted read-only; may appear after boot)
EXECUTOR_AUTH_CLIENT_SECRET_FILE=/app/gateway-data/jwt/executor-secret

# Direct mode (bypass gateway) — must ALSO blank the client id to disable auth
EXECUTOR_UPSTREAM_URL=http://agentic-net-master:8082
EXECUTOR_AUTH_CLIENT_ID=

Multiple Executors + Executor Selection

All compose files run TWO executors by default: agentic-net-executor (id agentic-net-executor-default, port 8084) and agentic-net-executor-2 (id agentic-net-executor-2, port 8086). Identity is EXECUTOR_ID; per-executor model allowlist is EXECUTOR_MODELS (sent as allowedModels on discover/poll).

A command transition picks its executor in the inscription:

"action": { "type": "command", "executorId": "agentic-net-executor-2", ... }

Resolution order on master: action.executorIdassignedAgent leaf (default agentic-net-executor-default). "*" offers the work to every polling executor — the first token reservation wins, and while the command runs on one executor the master answers the others with CONTINUE for that transition. docker-compose.multi-master.yml adds a second master partitioned by model (MASTER_1_MODELS / MASTER_2_MODELS).

CRITICAL — Stdin Blocking Issue

When running CLI tools via the executor, always redirect stdin:

# WRONG — Will hang indefinitely
claude -p 'prompt'

# CORRECT — Redirect stdin to prevent blocking
claude -p 'prompt' --no-session-persistence < /dev/null

Command Token Schema

{
  "kind": "command",
  "id": "unique-cmd-id",
  "executor": "bash",
  "command": "exec",
  "args": {
    "command": "your-shell-command-here",
    "workingDir": "/path/to/directory",
    "timeoutMs": 60000,
    "captureStderr": true,
    "env": {"KEY": "value"}
  },
  "expect": "text",
  "meta": {"correlationId": "req-001"}
}

Command Result Format

{
  "batchPrefix": "transition-id-timestamp",
  "batchResults": [{
    "executor": "bash",
    "results": [{"id": "cmd-id", "status": "SUCCESS", "output": {"exitCode": 0, "stdout": "...", "stderr": "", "success": true}, "durationMs": 15}],
    "totalCount": 1, "successCount": 1, "failedCount": 0
  }],
  "success": true
}

agentic-net-cli

Purpose: Command-line interface for AgenticNetOS operations.

  • Technology: TypeScript, Node.js 22, ESM bundle via tsup
  • Build: cd agentic-net-cli && npm install && npx tsup (105KB ESM bundle)
  • Run: node dist/bin/agenticos.js or link via npm link
  • Dual mode: --direct (node:8080 + master:8082) or gateway (:8083 with JWT)
  • LLM providers: anthropic, claude-code, codex, ollama, routed
  • RoutedLlmProvider: Routes between "worker" (cheap) and "thinker" (reasoning) models
  • Claude Code provider: --provider claude-code uses claude -p with --tools ''
  • Tool use via text: Embeds <tool_call> XML protocol in system prompt
  • License: "SEE LICENSE IN LICENSE.md" in package.json

agentic-net-chat

Purpose: Telegram bot integration for conversational workflows.

  • Technology: TypeScript, Node.js 22, grammy library
  • Build: cd agentic-net-chat && npm install && npx tsup
  • Dependency: @agenticos/cli via file:../agentic-net-cli (monorepo workspace link)
  • Sessions: Auto-expiration (4-hour TTL), auto-compaction (30K token threshold)
  • Limits: 100 iterations, 100 tool calls, 3 think calls, 50 consecutive same-tool calls
  • License: "SEE LICENSE IN LICENSE.md" in package.json

Note on Docker build context: The chat Dockerfile uses the repo root as build context (not just agentic-net-chat/) because it needs to copy agentic-net-cli/ for the workspace dependency.

agentic-net-mcp

Purpose: MCP (Model Context Protocol) server — exposes an AgenticNetOS stack to any MCP client (Claude Code, Claude Desktop, Cursor, agent frameworks) as persistent working memory that runs plus a net-building workbench. Design doc: agentic-net-mcp/DESIGN.md.

  • Technology: TypeScript, Node.js 22, @modelcontextprotocol/sdk; reuses @agenticos/cli's GatewayClient/MasterApi/NodeApi/ToolExecutor via file:../agentic-net-cli (bundled inline by tsup noExternal — same pattern as chat, including the repo-root Docker build context)
  • Build / test: cd agentic-net-mcp && npm install && npx tsup && npm test (32 hermetic vitest tests: scope guard, blueprint invariants, protocol registration shapes, template executor)
  • Transports: stdio (default; npx @agenticnets/mcp, claude mcp add) and streamable HTTP (AGENTICOS_MCP_TRANSPORT=http, bearer-token-protected POST /mcp — used by the compose service)
  • Tools (curated lowercase plus an optional native UPPERCASE layer; every tool advertises MCP readOnlyHint/destructiveHint annotations derived from the scope guard's mutates flag, and every response echoes its effective scope: {model, session} unless the handler already states it — see protocol-hardening.md for the trap classes behind this). Native layer = FULL platform parity when AGENTICOS_NATIVE_TOOLS=all (the backward-compatible default outside Desktop; Desktop Lite sets curated): every ToolExecutor tool (the same catalog agent transitions use in-net) auto-registered from the CLI's getAvailableTools(FULL) + buildToolSchemas with real descriptions/schemas — new platform tools appear automatically after a catalog sync; excluded only THINK/DONE/FAIL (agent-loop primitives); rw-mode only; browsable via the agenticnets://tool-catalog resource. Curated layer: memory layer memory_write / memory_recall / memory_link / memory_graph; net-building deploy_template, create_net, add_place, add_transition / add_transitions (kind-aware pre-wired inscriptions: map/llm/http/command/agent/link), delete_tokens (bounded ArcQL query+delete — filtered, but 100/call and one round trip per token) / clear_place (whole-place reset in ONE batch via master POST /runtime/places/{id}/tokens/deleteAll; place id and arcs survive, lease-guarded with force, optional expectCount interlock — measured 5000 tokens in 0.3s vs ~500/min through the per-token path), set_schedule, fire_once (preserveRunning smoke test), start/stop_transition, create_persona, spawn_persona (complete self-driving agent-persona net — charter + task inbox + started agent transition + output; run several in parallel), scaffold_tool_net, invoke_tool_net, crystallize_session (record a session's summary + steps to memory AND bake the steps into a replayable command tool-net); model control pause_model (kill switch — stops ALL running transitions, writes an audit pause-record token to p-mcp-control) / resume_model (restores exactly the paused set; command lanes re-register RUNNING on the executor's next poll, ~seconds — trust resumedCount); model lifecycle list_models (all models + per-connection allowed flag) / create_model (mint a NEW model + optional template deploy; joins the session allowlist so scope.multiModel becomes true and every tool exposes the model param even for a 1-model config; gated by AGENTICOS_ALLOW_MODEL_CREATE, rw-only) — so the COMPLETE AgenticOS feature set (models/sessions/ nets/tokens) is reachable via MCP; DELETE_TRANSITION deregisters an orphaned runtime transition (stop+remove inscription/status/assignment; DELETE_NET gained deleteTransitions:true) — needed a new CLI MasterApi.deleteTransition (DELETE /runtime/transitions/{id}); known gap: node admin model removal 500s/404s through the gateway proxy (create works, remove deferred); NetHub hub_publish (net/session/model artifact, versioned, credential-scrubbed; tokens= none|config|all where config = -config/-charter place tokens + config:"true"-marked tokens) / hub_search (local or a peer via remote; compact + paginated limit/offset + true total) / hub_show (inspect ONE artifact before installing — versions, kind, tokenPolicy, readme, size, shape) / hub_install (model-kind ⇒ create_new model + grantModel) / hub_add_remote (peer instance URL; P2P federation) — backed by master /api/hub (HubController/HubService/HubRemoteStore/HubRemoteClient) over the existing package registry; the 7 native HUB_* catalog tools auto-appear too. Gateway gateway.hub.public-catalog (AGENTICOS_HUB_PUBLIC_CATALOG, default false) opt-in-exposes anonymous GET /api/hub/public/** + /api/packages/** (folded under the same flag — default is "no token ⇒ nothing"); client-hosted execution host_transition / unhost_transition (an llm/agent transition built with start:false is NEVER on master — the MCP process itself executes it via the CLI's executeTransitionLocally on AGENTICOS_LLM_PROVIDER (default claude-code = local claude binary; also ollama/anthropic/openai + AGENTICOS_LLM_MODEL/_TIER); mode:watch polls the inbox, mode:once single-shot; stats in net_stats.hosted; hosted lanes run only while the session is connected — tokens wait safely otherwise); observability/debugging net_overview, query_tokens, event_trail, net_stats (LLM consumption + running/error transitions + scheduled cron/interval list + paused flag + tool-net usage + recent errors + executorCoverage: whether an ONLINE executor is actually polling this model — command lanes can look RUNNING with a full queue yet never fire when nothing polls, the classic "queued, no output" stall — the no-logs cockpit), list_executors (registered executors + coverageForModel: covered/allowedButIdle verdict for build-time executor choice AND debug-time "why don't my command lanes fire"), list_transitions (the model audit: kind + schedule + live status + places per transition in one call), scheduler_status (lastFiredAt/nextFireAt/eligibility/overdue per scheduled lane — the "my nets went silent" answer), llm_health (provider READY/MODEL_NOT_FOUND/UNREACHABLE pre-flight), readiness (the whole dependency chain in ONE call: gateway auth → node → model exists/state/workspace → llm provider → executor coverage, with per-layer verdicts + capabilities {build, llmLanes, commandLanes} + a problems list — run FIRST on a new connection or model; all four GET-based ⇒ readonly-safe), verify_inscription / dry_run_transition / diagnose_transition (per-transition diagnosis — for command transitions diagnose adds the executor-coverage check the master itself cannot see; rw-only — they travel as POST, readonly registers only net_stats from this group); usage_report (the token meter: ranked per-transition burn + burnSplit scheduled-vs-work, drill-down per transition; GET ⇒ readonly-safe — the measure→rank→retune→watch loop); agent-side MCP mcp_servers (read: whether THIS server can be handed to an agent transition and at which URL, which lanes already declare action.mcp and whether their role carries the m flag, and — with a transitionId — the catalog MASTER discovers with the real vault credentials via GET /api/agent/tools/mcp/catalog, WITHOUT firing the agent) / attach_mcp_server (write: adds the server to action.mcp, widens action.role with m, stores the credential; self:true attaches this Agentic-Nets server and writes its own bearer token straight to the vault so the secret never enters the client's context) — see agenticnets://docs/mcp-servers; knowledge pack: 17 curated md docs bundled into the binary (src/knowledge/*.md, tsup text loader) served as agenticnets://docs/{topic} + searched by search_knowledge (offline grep, registered in readonly too) — includes tool-catalog (rwxhludcts flags, global/local-first scoping, sha256 double-check), cost (the meter loop), nethub (export/import + self-contained packages) — content is leak-gated by test/knowledge-leaks.test.ts (scans every shipped string for credentials/IPs/paths/CI internals; size caps 8KB/doc, 64KB pack, 15KB instructions), so curated rewrites of private-repo knowledge can ship safely. ⚠️ agent role strings are the MASTER's positional rwxhludctsm (INVOKE_TOOL_NET is t-gated, personas c-gated, MCP_CALL m-gated — 11-char positional like rwxh------m, paired with the agent mcp param on add_transition); spawn_persona execute ⇒ rwxhl---t. The server instructions + recipes teach clients: 6-field cron scheduling (nets act overnight — always tell the user what you armed), spawning full Claude Code instances via command transitions (claude -p '…' --allowedTools … --no-session-persistence < /dev/null — stdin redirect mandatory), and the model-control contract ("switch it off" ⇒ pause_model, verify net_stats.paused). agent-persona note: spawn_persona workers auto-route via autoEmit:true, so verify_inscription reports a benign MISSING_EMIT warning on them (expected, not a failure — proven: task in → agent fires → result auto-lands in the output place).
  • Starter templates (deploy_template, idempotent; params via agenticnets://templates): working-memory (memory places + link graph + always-on LLM distiller; param distillPrompt), dev-team (token-free pipeline — the CONNECTED AGENT is the worker; param digestCron), brain (LLM panel + critic; params panelPrompt/criticPrompt), watcher (zero-LLM cron sentinel: probe url → log + webhook alert on non-200; params url/webhook/cron/label), blank
  • Claude Code hooks (agentic-net-mcp/hooks/, fail-open, config ~/.agenticnets/hooks.env): agenticnets-recall.sh (SessionStart → injects newest decisions/notes as additionalContext) + agenticnets-capture.sh (SessionEnd → session summary token to p-mem-inbox; distiller makes it durable). Gotcha pair: hook stdin must be cat-ed into a var BEFORE python3 - <<HEREDOC (the heredoc consumes stdin), and master's token POST body is {"data":{...}} (TokenCreateRequest).
  • Teach-the-client: rich instructions at initialize + agenticnets://docs/{concepts,arcql,recipes,security} resources + prompts (setup-working-memory, work-dev-team-backlog, capture-session, debug-net)
  • License: "SEE LICENSE IN LICENSE.md" in package.json

Configuration (env-first, no config files)

Env Meaning Default
AGENTICOS_MODELS Required. Model allowlist (comma-separated); first = default. Single model ⇒ tools expose NO model param; multiple ⇒ optional model validated per call (MODEL_NOT_ALLOWED otherwise) — (fail-fast)
AGENTICOS_GATEWAY_URL Gateway base (all traffic goes through /api + /node-api) http://localhost:8083
AGENTICOS_ADMIN_SECRET / AGENTICOS_GATEWAY_SECRET_FILE Client secret for the mode's client id — (required)
AGENTICOS_MODE rw | readonly — readonly registers ONLY the GET-based read tools (memory_recall, memory_graph, domain_memory_recall, net_overview, query_tokens, event_trail, net_stats, list_transitions, list_models, list_executors, llm_health, mcp_servers, readiness, scheduler_status, usage_report, search_knowledge) AND authenticates as agenticos-readonly, so the gateway itself 403s mutations (the POST-based diagnose/dry-run/verify diagnostics are rw-only) rw
AGENTICOS_SESSION Session name for MCP-created nets/places mcp
AGENTICOS_NODE_HOST Host injected into inscription presets/postsets ({model}@{host}); in-compose: agentic-net-node:8080 localhost:8080
AGENTICOS_MCP_TRANSPORT / AGENTICOS_MCP_HTTP_PORT / AGENTICOS_MCP_HTTP_TOKEN HTTP transport toggle, port, required bearer token stdio / 8091 / —
AGENTICOS_MCP_HTTP_HOST Bind interface for the HTTP transport (desktop bundles set 127.0.0.1); GET /health answers 200 pre-auth for supervisors 0.0.0.0
AGENTICOS_MCP_SELF_URL The URL at which master reaches this server, so it can be handed to an agent transition via action.mcp (mcp_servers / attach_mcp_server {self:true}). The bind host is not the answer: 0.0.0.0 is not routable and a container's loopback is not master's. Compose sets http://agentic-net-mcp:8091/mcp and puts the service on the backend network http://127.0.0.1:{port}/mcp
AGENTICOS_NATIVE_TOOLS all registers curated + full native UPPERCASE catalog; curated registers the focused lowercase surface only (Desktop Lite default) all

Compose keys (deployment/.env): AGENTICOS_MCP_MODELS / _MODE / _SESSION / _HTTP_TOKEN (generate: openssl rand -hex 24), AGENTIC_NET_MCP_PORT (8091). Service is opt-in: COMPOSE_PROFILES=mcp docker compose -f docker-compose.hub-only.yml up -d agentic-net-mcp.

Ready-to-paste (Claude Code, local stack):

claude mcp add agenticnets \
  -e AGENTICOS_GATEWAY_URL=http://localhost:8083 \
  -e AGENTICOS_ADMIN_SECRET=$(cat deployment/data/gateway/jwt/admin-secret) \
  -e AGENTICOS_MODELS=my-memory \
  -- npx @agenticnets/mcp

Deliberately stable: the curated lowercase surface. The native list tracks the platform catalog automatically and is exposed when AGENTICOS_NATIVE_TOOLS=all; Desktop Lite selects the curated surface to reduce MCP discovery noise. The p-mem-* memory-place conventions (templates upgrade the same places the tools write to), and the engine-gotcha defaults baked into inscriptions (non-empty preset arcql, llm timeoutMs 240s, catch-all emits). Scoping honesty: the allowlist is enforced in-process; the underlying gateway credential is NOT model-scoped (no per-model authz exists in the platform yet) — it protects against client/LLM mistakes and prompt injection, not a malicious operator of the MCP process.

agentic-net-vault (Port 8085)

Purpose: Secrets management service for transition credentials. Wraps OpenBao (open-source Vault fork) as the secrets backend.

  • Technology: Spring Boot 3.5.5, Java 21, spring-vault-core 3.1.1
  • Backend: OpenBao (MPL 2.0, API-compatible with HashiCorp Vault)
  • Backend selector: VAULT_BACKEND=openbao (default) or file — self-contained AES-256-GCM encrypted local files (desktop/light installs, no OpenBao): one file per {modelId}/{transitionId} under VAULT_FILE_PATH (default ~/.agenticos/vault/credentials), key auto-generated 0600 at VAULT_FILE_KEY_FILE (default ~/.agenticos/vault/vault.key). Ids are AAD-bound into the ciphertext; reads fail closed (502) on wrong key/corrupt file. REST contract identical across backends — master needs no changes.
  • Build: cd agentic-net-vault && ./mvnw clean package -DskipTests
  • KV v2 path: secret/agenticos/credentials/{modelId}/{transitionId}
  • API: CRUD for transition credentials (PUT/GET/DELETE /api/vault/{modelId}/transitions/{transitionId}/credentials)
  • Auth: Token auth (dev mode) or AppRole (production)
  • Network: agenticnetos-backend only — not exposed to host

sa-blobstore (Port 8090)

Purpose: Distributed blob storage service.

  • Technology: Spring Boot, Java 21
  • Build: cd sa-blobstore && ./mvnw clean package -DskipTests
  • Dockerfile: Multi-stage with production and development targets

Deployment

Compose Files

Two deployment modes in deployment/:

File Description
docker-compose.yml Hybrid — Closed-source from Hub, open-source built locally
docker-compose.hub-only.yml All pre-built — Everything from Docker Hub
docker-compose.hub-only.no-monitoring.yml Hub-only without the monitoring stack
docker-compose.multi-master.yml Two masters + two executors — masters partitioned by model (MASTER_1_MODELS/MASTER_2_MODELS), self-registered with the gateway (no seed master); for staging validation of the multi-master path

Networks

Network Services
agenticnetos-backend node, master, executor, gateway, vault, openbao, monitoring, registry
agenticnetos-clients gateway, gui, cli, chat

Gateway bridges both networks.

Service Sources

Service Hybrid Compose Hub-Only Compose
agentic-net-node image: (Hub) image: (Hub)
agentic-net-master image: (Hub) image: (Hub)
agentic-net-gui image: (Hub) image: (Hub)
agentic-net-gateway build: (local) image: (Hub)
agentic-net-executor build: (local) image: (Hub)
agentic-net-vault build: (local) image: (Hub)
agentic-net-cli build: (local) image: (Hub)
agentic-net-chat build: (local) image: (Hub)
sa-blobstore build: (local) image: (Hub)

Quick Start

cd deployment
cp .env.template .env
# Edit .env — at minimum set LLM_PROVIDER and API keys

# Option A: All pre-built
docker compose -f docker-compose.hub-only.yml up -d

# Option B: Hybrid (build open-source locally)
docker compose up -d

Gateway Auto-Auth

Gateway generates an admin secret on first startup. CLI and Chat mount the gateway data volume read-only to auto-acquire JWT tokens:

volumes:
  - ./data/gateway:/app/gateway-data:ro

Environment Configuration

Copy .env.template to .env. Key settings:

# LLM
LLM_PROVIDER=ollama                              # or "claude"
ANTHROPIC_API_KEY=                                # for Claude provider
OLLAMA_BASE_URL=http://host.docker.internal:11434 # for Ollama provider

# Security (auto-generated by gateway if empty)
AGENTICOS_ADMIN_SECRET=
AGENTICOS_SETTINGS_KEY=

# Telegram (optional)
TELEGRAM_BOT_ENABLED=false
TELEGRAM_BOT_TOKEN=

Building & Pushing Images

# Build and push all open-source services
./deployment/scripts/build-and-push.sh 1.0.0

# Dry run (build only)
./deployment/scripts/build-and-push.sh 1.0.0 --dry-run

# Single service
./deployment/scripts/build-and-push.sh 1.0.0 --only gateway

Services: gateway, executor, vault, cli, chat, blobstore

Monitoring

Stack: Grafana + Prometheus + Tempo + OpenTelemetry Collector + Loki/Alloy (logs)

Service URL Notes
Grafana http://localhost:3000 admin/admin
Prometheus http://localhost:9090
Tempo http://localhost:3200 Distributed tracing
Loki http://localhost:3100 Log aggregation — query via Grafana Explore ({container="..."})

All AgenticNetOS services export metrics and traces via OpenTelemetry (OTLP to otel-collector:4318).

Logs: every Java service logs to stdout AND a rolling file (./data/logs/<service>/, 50MB / 7 days / 500MB cap) via one standard logback-spring.xml. Alloy tails every container's stdout through the Docker socket (read-only) and pushes to Loki — labels project/service/container; the log pattern's [trace_id,span_id] links to Tempo. Loki is hard-capped (72h retention, 5MB/s ingest — monitoring/config/loki.yaml).

Configs in monitoring/config/, Grafana dashboards in monitoring/grafana-provisioning/.

Port Allocation

Port Service
8080 agentic-net-node (closed-source, Hub)
8082 agentic-net-master (closed-source, Hub)
8083 agentic-net-gateway
8084 agentic-net-executor
8085 agentic-net-vault
8086 agentic-net-executor-2
8087 agentic-net-master-2 (multi-master compose only)
4200 agentic-net-gui (closed-source, Hub)
8090 sa-blobstore
8091 agentic-net-mcp (HTTP transport, opt-in mcp profile)
3000 Grafana
9090 Prometheus
3200 Tempo
3100 Loki (log aggregation, fed by Alloy)
4317/4318 OpenTelemetry Collector (gRPC/HTTP)

Licensing Model

What License File
Source code in this repo BSL 1.1 LICENSE.md
Docker images: node, master, gui Proprietary EULA PROPRIETARY-EULA.md

BSL 1.1 summary: Free for non-production use (dev, test, personal, education). Commercial production use requires a license. Converts to Apache 2.0 on 2030-02-22.

EULA summary: Free for personal/educational/non-commercial use. Commercial use requires contacting alexejsailer@gmail.com.

Both carry strong NO WARRANTY / BETA disclaimers.

Relationship to core/

This repo (agentic-nets/) was split from the AgenticNetOS monorepo. The open-source services were moved here (not copied). The private repo at ../core/ retains the closed-source services and full git history.

The closed-source services (node, master, gui) are consumed here only as Docker Hub images — their source code is not in this repository.

Key Lessons Learned

  • Docker Compose prefixes network names with project name — use name: in network definition to get exact names
  • agentic-net-chat Dockerfile needs repo root as build context because of file:../agentic-net-cli dependency
  • Executor stdin blocking: always redirect < /dev/null when running CLI tools via command transitions
  • Gateway auto-generates admin secret — CLI/chat mount gateway volume read-only for auto-auth
  • .env files must never be committed (.gitignore blocks them) — use .env.template