Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -168,7 +168,7 @@ agentops-showcase/
│ └── skills/ # Project-level Cursor agent skills
├── AGENTS.md # This file — AI agent context
├── README.md # Project overview, quick start
├── assets/ # Diagrams (overall-architecture.png for README; strategy-image.png)
├── assets/ # Diagrams (overall-architecture.png/.gif for README; strategy-image.png)
├── config/
│ ├── openclaw.json.tpl # OpenClaw harness config template
│ └── openshell/ # OpenShell sandbox policies (Landlock, egress)
Expand Down Expand Up @@ -216,6 +216,7 @@ agentops-showcase/
│ ├── validate-demo-external-css.sh # Lint docs/demo HTML/JS for external CSS only
│ ├── validate-demo-ui.sh # CSS lint + demo unit tests (no cluster)
│ ├── export-readme-architecture.sh # Playwright PNG for README (v5/live.html step 0)
│ ├── export-readme-architecture-gif.sh # Playwright frame capture + ffmpeg GIF (hops 0–6 default)
│ ├── demo-observability-proxy.py
│ ├── demo-enable-guardrails.sh # Live demo Change 2: NeMo inference path
│ ├── demo-disable-guardrails.sh # Reset to direct MaaS
Expand Down
5 changes: 4 additions & 1 deletion Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,16 @@ DEPLOY_DIR := deploy

.DEFAULT_GOAL := help

.PHONY: help export-architecture
.PHONY: help export-architecture export-architecture-gif
help:
@$(MAKE) -C $(DEPLOY_DIR) help

export-architecture:
@./scripts/export-readme-architecture.sh

export-architecture-gif:
@./scripts/export-readme-architecture-gif.sh

# Forward any other target to deploy/Makefile (demo, deploy-all, validate-full, …)
%:
@$(MAKE) -C $(DEPLOY_DIR) $@
55 changes: 35 additions & 20 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,28 +16,43 @@ This project demonstrates the **BYOA (Bring Your Own Agent)** approach from the

## Platform Stack

```mermaid
flowchart TB
subgraph USER["USER LAYER"]
UI["End user → Control UI<br/>(openclaw-ui-proxy · nginx mTLS bridge)"]
end

subgraph AGENT["AGENT LAYER · BYOA"]
OC["OpenClaw harness<br/>Agent Sandbox · Landlock policies"]
end

subgraph PLATFORM["PLATFORM LAYER · Red Hat"]
GW["OpenShell Gateway — egress choke · key injection"]
ML["MLflow — tracing + prompt registry"]
NG["NeMo Guardrails · TrustyAI"]
end

subgraph INFERENCE["INFERENCE LAYER"]
IR["inference.local → NeMo → MaaS → LLM"]
end

subgraph INFRA["INFRASTRUCTURE"]
OCP["OpenShift + RHOAI 3.x · Agent Sandbox Operator (OLM)"]
end

USER --> AGENT --> PLATFORM --> INFERENCE --> INFRA
```
┌─────────────────────────────────────────────────────────────┐
│ USER LAYER │
│ End user → Control UI (openclaw-ui-proxy, nginx mTLS bridge)│
├─────────────────────────────────────────────────────────────┤
│ AGENT LAYER (BYOA — demo harness: OpenClaw) │
│ OpenClaw in Agent Sandbox (OpenShell policies: Landlock) │
├─────────────────────────────────────────────────────────────┤
│ PLATFORM LAYER (Red Hat) │
│ OpenShell Gateway (egress choke point, key injection) │
│ MLflow — tracing + prompt registry (background spans) │
│ NeMo Guardrails via TrustyAI (enabled live in Change 2) │
├─────────────────────────────────────────────────────────────┤
│ INFERENCE LAYER │
│ inference.local → [NeMo] → MaaS → LLM (external MaaS) │
├─────────────────────────────────────────────────────────────┤
│ INFRASTRUCTURE │
│ OpenShift + RHOAI 3.x · Agent Sandbox Operator (OLM) │
└─────────────────────────────────────────────────────────────┘
```

The agent harness is interchangeable (BYOA); the platform stack works regardless of framework. Interactive architecture map (live): [v5/live.html](docs/demo/v5/live.html) step **Overall Demo**. Deep dive: [Agent Sandbox and OpenShell — How It Works](docs/AGENT-SANDBOX-AND-OPENSHELL.md).
| Layer | Tag | Components |
|---|---|---|
| **User** | ![Control UI](https://img.shields.io/badge/Control-UI-0066cc?style=flat-square) | Control UI via `openclaw-ui-proxy` (nginx mTLS bridge + password auth) |
| **Agent (BYOA)** | ![BYOA](https://img.shields.io/badge/Agent-BYOA-e00?style=flat-square) | OpenClaw in Agent Sandbox — interchangeable harness; Landlock + egress policies |
| **Platform** | ![Red Hat](https://img.shields.io/badge/Platform-Red_Hat-ee0000?style=flat-square) ![MLflow](https://img.shields.io/badge/Traces-MLflow-ffc107?style=flat-square&labelColor=333) | OpenShell · MLflow · NeMo Guardrails (TrustyAI) |
| **Inference** | ![MaaS](https://img.shields.io/badge/Inference-MaaS-0066cc?style=flat-square) | `inference.local` → MaaS — router injects API key; credentials never enter the sandbox |
| **Infrastructure** | ![RHOAI](https://img.shields.io/badge/OpenShift-RHOAI-ee0000?style=flat-square) | OCP + RHOAI 3.x — pinned operators; Agent Sandbox via OLM |

> **BYOA:** the agent harness is interchangeable; the platform stack works regardless of framework.
> **Live map:** [v5/live.html](docs/demo/v5/live.html) step **Overall Demo** · **Deep dive:** [Agent Sandbox and OpenShell — How It Works](docs/AGENT-SANDBOX-AND-OPENSHELL.md) · **Full matrix:** [AGENTS.md § Tech Stack](AGENTS.md#tech-stack)

## Understanding the Platform

Expand Down
Binary file added assets/overall-architecture.gif
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
94 changes: 94 additions & 0 deletions assets/preview/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,94 @@
# Architecture GIF previews (local, temporary)

**Do not commit this folder.** It exists only to compare three animated variants of the v5 **Overall Demo** FlowStory diagram before picking one for the README (or dropping the GIF entirely).

Source: `docs/demo/v5/live.html#step-0` (same canvas as `assets/overall-architecture.png`).

## Variants in this folder

| File | Hops (`jumpTo` index) | Narrative | Frames | FPS | ~Duration |
|------|------------------------|-----------|--------|-----|-----------|
| `overall-architecture-request-path.gif` | 0–6 | End user → OpenClaw → inference → NeMo → MaaS → LLM | 7 | 2 | ~3.5 s |
| `overall-architecture-request-response.gif` | 0–13 | Above + LLM response path + Landlock | 14 | 2 | ~7 s |
| `overall-architecture-full.gif` | 0–21 | Full baseline (+ egress + MLflow trace) | 22 | 3 | ~7.3 s |

Open each GIF side by side in the IDE or a browser tab to compare pacing and scope.

## Regenerate previews

From repo root (requires `ffmpeg`, Node, Playwright Chromium):

```bash
./scripts/export-architecture-gif-preview.sh
```

Single variant with custom output:

```bash
cd tests
ARCH_GIF_LAST_INDEX=13 \
ARCH_GIF_FPS=2 \
ARCH_GIF_OUTPUT=../assets/preview/my-variant.gif \
PLAYWRIGHT_BROWSERS_PATH=0 node export-architecture-gif.mjs
```

Useful env vars (see `tests/export-architecture-gif.mjs` header):

| Variable | Default | Purpose |
|----------|---------|---------|
| `ARCH_GIF_FIRST_INDEX` | `0` | First hop index |
| `ARCH_GIF_LAST_INDEX` | `6` | Last hop index |
| `ARCH_GIF_FPS` | `2` | GIF playback rate |
| `ARCH_GIF_FRAME_DELAY_MS` | `700` | Wait after each `jumpTo` before screenshot |
| `ARCH_GIF_WIDTH` | `1200` | Output width (px) |
| `ARCH_GIF_INCLUDE_RESET` | `false` | Extra idle frame before hop 1 |
| `ARCH_GIF_OUTPUT` | `assets/overall-architecture.gif` | Output path |

Official export (after a variant is chosen):

```bash
make export-architecture-gif
# example: ARCH_GIF_LAST_INDEX=13 make export-architecture-gif
```

## When you pick a winner — cleanup checklist

### A) Keep one GIF in the repo

1. Copy the chosen file to the canonical path:
```bash
cp assets/preview/overall-architecture-<winner>.gif assets/overall-architecture.gif
```
2. Set defaults in `tests/export-architecture-gif.mjs` (`ARCH_GIF_LAST_INDEX`, `ARCH_GIF_FPS`) to match the winner so `make export-architecture-gif` reproduces it.
3. **Delete temporary preview boilerplate:**
- `assets/preview/` (this entire directory, including this README and the three `*.gif` files)
- `scripts/export-architecture-gif-preview.sh`
4. Optionally wire `assets/overall-architecture.gif` into root `README.md` next to the PNG.
5. Commit only `assets/overall-architecture.gif` + any default/env doc tweaks — not `assets/preview/`.

### B) Do not ship a GIF

1. **Delete preview artifacts:**
- `assets/preview/` (entire directory)
- `scripts/export-architecture-gif-preview.sh`
2. **Delete GIF export tooling** (if no longer needed):
- `tests/export-architecture-gif.mjs`
- `scripts/export-readme-architecture-gif.sh`
- `assets/overall-architecture.gif` (if present)
- `make export-architecture-gif` target in root `Makefile`
- `export-architecture-gif` script in `tests/package.json`
- GIF section in `docs/demo/README.md`
- `export-readme-architecture-gif.sh` line in `AGENTS.md`
3. Keep `make export-architecture` (PNG) — that remains the documented static diagram.

## Related (keep unless option B)

| Path | Role |
|------|------|
| `tests/export-architecture-gif.mjs` | Playwright frame capture + ffmpeg assembly |
| `scripts/export-readme-architecture-gif.sh` | Wrapper for `make export-architecture-gif` |
| `tests/export-architecture-diagram.mjs` | Static PNG export (unchanged) |

---

*Temporary local note — remove with `assets/preview/` once a decision is made.*
Binary file added assets/preview/overall-architecture-full.gif
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
9 changes: 9 additions & 0 deletions docs/demo/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -180,6 +180,15 @@ make export-architecture

Output: [`assets/overall-architecture.png`](../../assets/overall-architecture.png) (baseline flow with all hops revealed). Commit the PNG after regenerating — CI does not auto-export or validate it.

Animated GIF (request path hops 0–6 by default; requires `ffmpeg`):

```bash
make export-architecture-gif
# full baseline: ARCH_GIF_LAST_INDEX=21 make export-architecture-gif
```

Output: [`assets/overall-architecture.gif`](../../assets/overall-architecture.gif). Same manual-only policy as the PNG.

## Deprecated (dev / bookmarks only)

Do not use these on stage — v5 embeds the same maps in-card.
Expand Down
127 changes: 127 additions & 0 deletions docs/preview/platform-stack-preview.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,127 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Platform Stack preview — README</title>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/github-markdown-css/5.6.1/github-markdown-light.min.css">
<script type="module">
import mermaid from "https://cdn.jsdelivr.net/npm/mermaid@11/dist/mermaid.esm.min.mjs";
mermaid.initialize({ startOnLoad: true, theme: "neutral", securityLevel: "loose" });
</script>
<style>
body {
background: #f6f8fa;
margin: 0;
padding: 2rem 1rem 4rem;
font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Helvetica, Arial, sans-serif;
}
.banner {
max-width: 980px;
margin: 0 auto 1rem;
padding: 0.75rem 1rem;
background: #ddf4ff;
border: 1px solid #54aeff66;
border-radius: 6px;
color: #0969da;
font-size: 14px;
}
.markdown-body {
box-sizing: border-box;
min-width: 200px;
max-width: 980px;
margin: 0 auto;
padding: 2rem;
background: #fff;
border: 1px solid #d0d7de;
border-radius: 6px;
}
.markdown-body table img { vertical-align: middle; }
.markdown-body .mermaid { text-align: center; margin: 1rem 0; }
</style>
</head>
<body>
<div class="banner">
Local preview of <strong>README.md § Platform Stack</strong> — mirrors GitHub rendering (Mermaid + badges + table).
Edit <code>README.md</code> and refresh; this file is for preview only.
</div>

<article class="markdown-body">
<h2>Platform Stack</h2>

<pre class="mermaid">
flowchart TB
subgraph USER["USER LAYER"]
UI["End user → Control UI<br/>(openclaw-ui-proxy · nginx mTLS bridge)"]
end

subgraph AGENT["AGENT LAYER · BYOA"]
OC["OpenClaw harness<br/>Agent Sandbox · Landlock policies"]
end

subgraph PLATFORM["PLATFORM LAYER · Red Hat"]
GW["OpenShell Gateway — egress choke · key injection"]
ML["MLflow — tracing + prompt registry"]
NG["NeMo Guardrails · TrustyAI"]
end

subgraph INFERENCE["INFERENCE LAYER"]
IR["inference.local → NeMo → MaaS → LLM"]
end

subgraph INFRA["INFRASTRUCTURE"]
OCP["OpenShift + RHOAI 3.x · Agent Sandbox Operator (OLM)"]
end

USER --> AGENT --> PLATFORM --> INFERENCE --> INFRA
</pre>

<table>
<thead>
<tr>
<th>Layer</th>
<th>Tag</th>
<th>Components</th>
</tr>
</thead>
<tbody>
<tr>
<td><strong>User</strong></td>
<td><img src="https://img.shields.io/badge/Control-UI-0066cc?style=flat-square" alt="Control UI"></td>
<td>Control UI via <code>openclaw-ui-proxy</code> (nginx mTLS bridge + password auth)</td>
</tr>
<tr>
<td><strong>Agent (BYOA)</strong></td>
<td><img src="https://img.shields.io/badge/Agent-BYOA-e00?style=flat-square" alt="BYOA"></td>
<td>OpenClaw in Agent Sandbox — interchangeable harness; Landlock + egress policies</td>
</tr>
<tr>
<td><strong>Platform</strong></td>
<td>
<img src="https://img.shields.io/badge/Platform-Red_Hat-ee0000?style=flat-square" alt="Red Hat">
<img src="https://img.shields.io/badge/Traces-MLflow-ffc107?style=flat-square&labelColor=333" alt="MLflow">
</td>
<td>OpenShell · MLflow · NeMo Guardrails (TrustyAI)</td>
</tr>
<tr>
<td><strong>Inference</strong></td>
<td><img src="https://img.shields.io/badge/Inference-MaaS-0066cc?style=flat-square" alt="MaaS"></td>
<td><code>inference.local</code> → MaaS — router injects API key; credentials never enter the sandbox</td>
</tr>
<tr>
<td><strong>Infrastructure</strong></td>
<td><img src="https://img.shields.io/badge/OpenShift-RHOAI-ee0000?style=flat-square" alt="RHOAI"></td>
<td>OCP + RHOAI 3.x — pinned operators; Agent Sandbox via OLM</td>
</tr>
</tbody>
</table>

<blockquote>
<p><strong>BYOA:</strong> the agent harness is interchangeable; the platform stack works regardless of framework.<br>
<strong>Live map:</strong> <a href="../demo/v5/live.html">v5/live.html</a> step <strong>Overall Demo</strong> ·
<strong>Deep dive:</strong> <a href="../AGENT-SANDBOX-AND-OPENSHELL.md">Agent Sandbox and OpenShell — How It Works</a> ·
<strong>Full matrix:</strong> <a href="../../AGENTS.md#tech-stack">AGENTS.md § Tech Stack</a></p>
</blockquote>
</article>
</body>
</html>
60 changes: 60 additions & 0 deletions scripts/export-architecture-gif-preview.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
#!/usr/bin/env bash
# Generate three temporary GIF variants for comparison (not for commit).
set -euo pipefail

SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
ROOT_DIR="$(cd "${SCRIPT_DIR}/.." && pwd)"
TESTS_DIR="${ROOT_DIR}/tests"
PREVIEW_DIR="${ROOT_DIR}/assets/preview"

require_cmd() {
if ! command -v "$1" >/dev/null 2>&1; then
echo "error: required command not found: $1" >&2
exit 1
fi
}

require_cmd python3
require_cmd node
require_cmd npm
require_cmd ffmpeg

if [[ ! -d "${TESTS_DIR}/node_modules/@playwright/test" ]]; then
echo "==> Installing test dependencies"
(cd "${TESTS_DIR}" && npm ci)
fi

export PLAYWRIGHT_BROWSERS_PATH=0
(cd "${TESTS_DIR}" && npx playwright install chromium)

mkdir -p "${PREVIEW_DIR}"

run_variant() {
local name="$1"
local last_index="$2"
local fps="$3"
local out="${PREVIEW_DIR}/overall-architecture-${name}.gif"

echo ""
echo "==> Variant: ${name} (hops 0..${last_index}, ${fps} fps) -> ${out}"
(
cd "${TESTS_DIR}"
ARCH_GIF_LAST_INDEX="${last_index}" \
ARCH_GIF_FPS="${fps}" \
ARCH_GIF_OUTPUT="${out}" \
node export-architecture-gif.mjs
)
}

# 1) Request path only — End user through LLM (7 hops)
run_variant "request-path" 6 2

# 2) Request + response — through Landlock round-trip (14 hops)
run_variant "request-response" 13 2

# 3) Full baseline — all hops including egress + MLflow trace (22 hops)
run_variant "full" 21 3

echo ""
echo "==> Preview GIFs written to ${PREVIEW_DIR}/"
ls -lh "${PREVIEW_DIR}"/overall-architecture-*.gif
Loading
Loading