@desplega.ai/agent-swarm 1.2.0 → 1.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.claude/settings.local.json +20 -1
- package/.dockerignore +3 -0
- package/.env.docker.example +22 -1
- package/.env.example +17 -0
- package/.github/workflows/docker-publish.yml +92 -0
- package/CONTRIBUTING.md +270 -0
- package/DEPLOYMENT.md +391 -0
- package/Dockerfile.worker +29 -1
- package/FAQ.md +19 -0
- package/LICENSE +21 -0
- package/MCP.md +249 -0
- package/README.md +105 -185
- package/assets/agent-swarm-logo-orange.png +0 -0
- package/assets/agent-swarm-logo.png +0 -0
- package/assets/agent-swarm.png +0 -0
- package/deploy/docker-push.ts +30 -0
- package/docker-compose.example.yml +137 -0
- package/docker-entrypoint.sh +223 -7
- package/package.json +13 -4
- package/{cc-plugin → plugin}/.claude-plugin/plugin.json +1 -1
- package/plugin/README.md +1 -0
- package/plugin/agents/.gitkeep +0 -0
- package/plugin/agents/codebase-analyzer.md +143 -0
- package/plugin/agents/codebase-locator.md +122 -0
- package/plugin/agents/codebase-pattern-finder.md +227 -0
- package/plugin/agents/web-search-researcher.md +109 -0
- package/plugin/commands/create-plan.md +415 -0
- package/plugin/commands/implement-plan.md +89 -0
- package/plugin/commands/research.md +200 -0
- package/plugin/commands/start-leader.md +101 -0
- package/plugin/commands/start-worker.md +56 -0
- package/plugin/commands/swarm-chat.md +78 -0
- package/plugin/commands/todos.md +66 -0
- package/plugin/commands/work-on-task.md +44 -0
- package/plugin/skills/.gitkeep +0 -0
- package/scripts/generate-mcp-docs.ts +415 -0
- package/slack-manifest.json +69 -0
- package/src/be/db.ts +1431 -25
- package/src/cli.tsx +135 -11
- package/src/commands/lead.ts +13 -0
- package/src/commands/runner.ts +255 -0
- package/src/commands/setup.tsx +5 -5
- package/src/commands/worker.ts +8 -220
- package/src/hooks/hook.ts +108 -14
- package/src/http.ts +361 -5
- package/src/prompts/base-prompt.ts +131 -0
- package/src/server.ts +56 -0
- package/src/slack/app.ts +73 -0
- package/src/slack/commands.ts +88 -0
- package/src/slack/handlers.ts +281 -0
- package/src/slack/index.ts +3 -0
- package/src/slack/responses.ts +175 -0
- package/src/slack/router.ts +170 -0
- package/src/slack/types.ts +20 -0
- package/src/slack/watcher.ts +119 -0
- package/src/tools/create-channel.ts +80 -0
- package/src/tools/get-tasks.ts +54 -21
- package/src/tools/join-swarm.ts +28 -4
- package/src/tools/list-channels.ts +37 -0
- package/src/tools/list-services.ts +110 -0
- package/src/tools/poll-task.ts +47 -3
- package/src/tools/post-message.ts +87 -0
- package/src/tools/read-messages.ts +192 -0
- package/src/tools/register-service.ts +118 -0
- package/src/tools/send-task.ts +80 -7
- package/src/tools/store-progress.ts +9 -3
- package/src/tools/task-action.ts +211 -0
- package/src/tools/unregister-service.ts +110 -0
- package/src/tools/update-profile.ts +105 -0
- package/src/tools/update-service-status.ts +118 -0
- package/src/types.ts +110 -3
- package/src/utils/pretty-print.ts +224 -0
- package/thoughts/shared/plans/.gitkeep +0 -0
- package/thoughts/shared/plans/2025-12-18-inverse-teleport.md +1142 -0
- package/thoughts/shared/plans/2025-12-18-slack-integration.md +1195 -0
- package/thoughts/shared/plans/2025-12-19-agent-log-streaming.md +732 -0
- package/thoughts/shared/plans/2025-12-19-role-based-swarm-plugin.md +361 -0
- package/thoughts/shared/plans/2025-12-20-mobile-responsive-ui.md +501 -0
- package/thoughts/shared/plans/2025-12-20-startup-team-swarm.md +560 -0
- package/thoughts/shared/research/.gitkeep +0 -0
- package/thoughts/shared/research/2025-12-18-slack-integration.md +442 -0
- package/thoughts/shared/research/2025-12-19-agent-log-streaming.md +339 -0
- package/thoughts/shared/research/2025-12-19-agent-secrets-cli-research.md +390 -0
- package/thoughts/shared/research/2025-12-21-gemini-cli-integration.md +376 -0
- package/thoughts/shared/research/2025-12-22-setup-experience-improvements.md +264 -0
- package/tsconfig.json +3 -1
- package/ui/bun.lock +692 -0
- package/ui/index.html +22 -0
- package/ui/package.json +32 -0
- package/ui/pnpm-lock.yaml +3034 -0
- package/ui/postcss.config.js +6 -0
- package/ui/public/logo.png +0 -0
- package/ui/src/App.tsx +43 -0
- package/ui/src/components/ActivityFeed.tsx +415 -0
- package/ui/src/components/AgentDetailPanel.tsx +534 -0
- package/ui/src/components/AgentsPanel.tsx +549 -0
- package/ui/src/components/ChatPanel.tsx +1820 -0
- package/ui/src/components/ConfigModal.tsx +232 -0
- package/ui/src/components/Dashboard.tsx +534 -0
- package/ui/src/components/Header.tsx +168 -0
- package/ui/src/components/ServicesPanel.tsx +612 -0
- package/ui/src/components/StatsBar.tsx +288 -0
- package/ui/src/components/StatusBadge.tsx +124 -0
- package/ui/src/components/TaskDetailPanel.tsx +807 -0
- package/ui/src/components/TasksPanel.tsx +575 -0
- package/ui/src/hooks/queries.ts +170 -0
- package/ui/src/index.css +235 -0
- package/ui/src/lib/api.ts +161 -0
- package/ui/src/lib/config.ts +35 -0
- package/ui/src/lib/theme.ts +214 -0
- package/ui/src/lib/utils.ts +48 -0
- package/ui/src/main.tsx +32 -0
- package/ui/src/types/api.ts +164 -0
- package/ui/src/vite-env.d.ts +1 -0
- package/ui/tailwind.config.js +35 -0
- package/ui/tsconfig.json +31 -0
- package/ui/vite.config.ts +22 -0
- package/cc-plugin/README.md +0 -49
- package/cc-plugin/commands/setup-leader.md +0 -73
- package/cc-plugin/commands/start-worker.md +0 -64
- package/docker-compose.worker.yml +0 -35
- package/example-req-meta.json +0 -24
- /package/{cc-plugin → plugin}/hooks/hooks.json +0 -0
|
@@ -0,0 +1,137 @@
|
|
|
1
|
+
# Docker Compose for Agent Swarm
|
|
2
|
+
#
|
|
3
|
+
# Usage:
|
|
4
|
+
# docker-compose -f docker-compose.example.yml --env-file .env up -d
|
|
5
|
+
#
|
|
6
|
+
# What it does:
|
|
7
|
+
# - Sets up an API service and multiple worker/lead agents
|
|
8
|
+
# - Deploys 2 worker agents and 1 lead agent by default
|
|
9
|
+
# - Uses volumes for persistent storage of logs, db and agent workspaces
|
|
10
|
+
|
|
11
|
+
services:
|
|
12
|
+
api:
|
|
13
|
+
build:
|
|
14
|
+
context: .
|
|
15
|
+
dockerfile: Dockerfile
|
|
16
|
+
|
|
17
|
+
environment:
|
|
18
|
+
- ENV=${ENV:-development}
|
|
19
|
+
- API_KEY=${API_KEY}
|
|
20
|
+
|
|
21
|
+
- MCP_BASE_URL=${MCP_BASE_URL:-http://localhost:3013}
|
|
22
|
+
- APP_URL=${APP_URL:-http://localhost:5175}
|
|
23
|
+
|
|
24
|
+
# Optional: Enable Slack integration
|
|
25
|
+
- SLACK_DISABLE=${SLACK_DISABLE:-false}
|
|
26
|
+
- SLACK_BOT_TOKEN=${SLACK_BOT_TOKEN:-}
|
|
27
|
+
- SLACK_APP_TOKEN=${SLACK_APP_TOKEN:-}
|
|
28
|
+
|
|
29
|
+
ports:
|
|
30
|
+
- "3013:3013"
|
|
31
|
+
|
|
32
|
+
volumes:
|
|
33
|
+
# For the sqlite database
|
|
34
|
+
- swarm_api:/app
|
|
35
|
+
|
|
36
|
+
restart: unless-stopped
|
|
37
|
+
|
|
38
|
+
worker-1:
|
|
39
|
+
build:
|
|
40
|
+
context: .
|
|
41
|
+
dockerfile: Dockerfile.worker
|
|
42
|
+
|
|
43
|
+
environment:
|
|
44
|
+
- CLAUDE_CODE_OAUTH_TOKEN=${CLAUDE_CODE_OAUTH_TOKEN}
|
|
45
|
+
- API_KEY=${API_KEY}
|
|
46
|
+
- AGENT_ID=${AGENT_ID}
|
|
47
|
+
- AGENT_ROLE=worker
|
|
48
|
+
|
|
49
|
+
- MCP_BASE_URL=${MCP_BASE_URL:-http://api:3013}
|
|
50
|
+
|
|
51
|
+
# Optional environment variables
|
|
52
|
+
- SESSION_ID=${SESSION_ID:-}
|
|
53
|
+
- YOLO=${YOLO:-false}
|
|
54
|
+
# GitHub credentials for git push and PR operations
|
|
55
|
+
- GITHUB_TOKEN=${GITHUB_TOKEN:-}
|
|
56
|
+
- GITHUB_EMAIL=${GITHUB_EMAIL:-}
|
|
57
|
+
- GITHUB_NAME=${GITHUB_NAME:-}
|
|
58
|
+
# Service registry URL (for service discovery)
|
|
59
|
+
- SWARM_URL=${SWARM_URL:-localhost}
|
|
60
|
+
|
|
61
|
+
ports:
|
|
62
|
+
# Expose service port for PM2 processes
|
|
63
|
+
- "${SERVICE_PORT:-3001}:3000"
|
|
64
|
+
|
|
65
|
+
volumes:
|
|
66
|
+
- swarm_logs:/logs
|
|
67
|
+
# Optional: mount a workspace directory for persistent work
|
|
68
|
+
- swarm_shared:/workspace/shared
|
|
69
|
+
- swarm_worker_1/personal:/workspace/personal
|
|
70
|
+
|
|
71
|
+
restart: unless-stopped
|
|
72
|
+
|
|
73
|
+
worker-2:
|
|
74
|
+
build:
|
|
75
|
+
context: .
|
|
76
|
+
dockerfile: Dockerfile.worker
|
|
77
|
+
|
|
78
|
+
environment:
|
|
79
|
+
- CLAUDE_CODE_OAUTH_TOKEN=${CLAUDE_CODE_OAUTH_TOKEN}
|
|
80
|
+
- API_KEY=${API_KEY}
|
|
81
|
+
- AGENT_ID=${AGENT_ID_2}
|
|
82
|
+
- AGENT_ROLE=worker
|
|
83
|
+
|
|
84
|
+
- MCP_BASE_URL=${MCP_BASE_URL:-http://api:3013}
|
|
85
|
+
|
|
86
|
+
# Same as above...
|
|
87
|
+
|
|
88
|
+
ports:
|
|
89
|
+
# Expose service port for PM2 processes
|
|
90
|
+
- "${SERVICE_PORT:-3002}:3000"
|
|
91
|
+
|
|
92
|
+
volumes:
|
|
93
|
+
- swarm_logs:/logs
|
|
94
|
+
- swarm_shared:/workspace/shared
|
|
95
|
+
- swarm_worker_2/personal:/workspace/personal
|
|
96
|
+
|
|
97
|
+
restart: unless-stopped
|
|
98
|
+
|
|
99
|
+
lead:
|
|
100
|
+
build:
|
|
101
|
+
context: .
|
|
102
|
+
dockerfile: Dockerfile.worker
|
|
103
|
+
|
|
104
|
+
environment:
|
|
105
|
+
- CLAUDE_CODE_OAUTH_TOKEN=${CLAUDE_CODE_OAUTH_TOKEN}
|
|
106
|
+
- API_KEY=${API_KEY}
|
|
107
|
+
- AGENT_ID=${AGENT_ID_LEAD}
|
|
108
|
+
|
|
109
|
+
# Important: Lead agent role
|
|
110
|
+
- AGENT_ROLE=lead
|
|
111
|
+
|
|
112
|
+
- MCP_BASE_URL=${MCP_BASE_URL:-http://api:3013}
|
|
113
|
+
|
|
114
|
+
# Same as above...
|
|
115
|
+
|
|
116
|
+
ports:
|
|
117
|
+
# Expose service port for PM2 processes
|
|
118
|
+
- "${SERVICE_PORT:-3003}:3000"
|
|
119
|
+
|
|
120
|
+
volumes:
|
|
121
|
+
- swarm_logs:/logs
|
|
122
|
+
- swarm_shared:/workspace/shared
|
|
123
|
+
- swarm_personal_lead:/workspace/personal
|
|
124
|
+
|
|
125
|
+
restart: unless-stopped
|
|
126
|
+
|
|
127
|
+
volumes:
|
|
128
|
+
swarm_api:
|
|
129
|
+
swarm_logs:
|
|
130
|
+
swarm_shared:
|
|
131
|
+
swarm_lead:
|
|
132
|
+
swarm_worker_1:
|
|
133
|
+
swarm_worker_2:
|
|
134
|
+
|
|
135
|
+
networks:
|
|
136
|
+
default:
|
|
137
|
+
driver: bridge
|
package/docker-entrypoint.sh
CHANGED
|
@@ -12,20 +12,79 @@ if [ -z "$API_KEY" ]; then
|
|
|
12
12
|
exit 1
|
|
13
13
|
fi
|
|
14
14
|
|
|
15
|
+
# Role defaults to worker, can be set to "lead"
|
|
16
|
+
ROLE="${AGENT_ROLE:-worker}"
|
|
15
17
|
MCP_URL="${MCP_BASE_URL:-http://host.docker.internal:3013}"
|
|
16
18
|
|
|
17
|
-
|
|
19
|
+
# Determine YOLO mode based on role
|
|
20
|
+
if [ "$ROLE" = "lead" ]; then
|
|
21
|
+
YOLO_MODE="${LEAD_YOLO:-false}"
|
|
22
|
+
else
|
|
23
|
+
YOLO_MODE="${WORKER_YOLO:-false}"
|
|
24
|
+
fi
|
|
25
|
+
|
|
26
|
+
echo "=== Agent Swarm ${ROLE^} ==="
|
|
18
27
|
echo "Agent ID: ${AGENT_ID:-<not set>}"
|
|
19
28
|
echo "MCP Base URL: $MCP_URL"
|
|
20
|
-
echo "YOLO Mode: $
|
|
29
|
+
echo "YOLO Mode: $YOLO_MODE"
|
|
21
30
|
echo "Session ID: ${SESSION_ID:-<auto-generated>}"
|
|
22
31
|
echo "Working Directory: /workspace"
|
|
23
32
|
echo "=========================="
|
|
24
33
|
|
|
34
|
+
# Initialize PM2 daemon for background service management
|
|
35
|
+
echo ""
|
|
36
|
+
echo "=== PM2 Initialization ==="
|
|
37
|
+
echo "PM2 Home: ${PM2_HOME:-~/.pm2}"
|
|
38
|
+
# Ensure PM2 home directory exists (for persistence in /workspace)
|
|
39
|
+
mkdir -p "${PM2_HOME:-$HOME/.pm2}"
|
|
40
|
+
pm2 startup > /dev/null 2>&1 || true
|
|
41
|
+
|
|
42
|
+
# Restore services from ecosystem (database-driven, more reliable than pm2 resurrect)
|
|
43
|
+
ECOSYSTEM_FILE="/workspace/ecosystem.config.js"
|
|
44
|
+
if [ -n "$AGENT_ID" ]; then
|
|
45
|
+
echo "Fetching ecosystem config from MCP server..."
|
|
46
|
+
if curl -s -f -H "Authorization: Bearer ${API_KEY}" \
|
|
47
|
+
-H "X-Agent-ID: ${AGENT_ID}" \
|
|
48
|
+
"${MCP_URL}/ecosystem" > /tmp/ecosystem.json 2>/dev/null; then
|
|
49
|
+
|
|
50
|
+
# Check if there are any apps to start
|
|
51
|
+
APP_COUNT=$(cat /tmp/ecosystem.json | jq -r '.apps | length' 2>/dev/null || echo "0")
|
|
52
|
+
|
|
53
|
+
if [ "$APP_COUNT" -gt "0" ]; then
|
|
54
|
+
echo "Found $APP_COUNT registered service(s)"
|
|
55
|
+
# Convert JSON to JS module
|
|
56
|
+
echo "module.exports = $(cat /tmp/ecosystem.json);" > "$ECOSYSTEM_FILE"
|
|
57
|
+
echo "Starting services from ecosystem file..."
|
|
58
|
+
pm2 start "$ECOSYSTEM_FILE" || true
|
|
59
|
+
pm2 list
|
|
60
|
+
else
|
|
61
|
+
echo "No services registered for this agent"
|
|
62
|
+
fi
|
|
63
|
+
rm -f /tmp/ecosystem.json
|
|
64
|
+
else
|
|
65
|
+
echo "Could not fetch ecosystem config (MCP server may be unavailable)"
|
|
66
|
+
fi
|
|
67
|
+
else
|
|
68
|
+
echo "AGENT_ID not set, skipping ecosystem restore"
|
|
69
|
+
fi
|
|
70
|
+
|
|
71
|
+
# Fallback: try pm2 resurrect for any locally saved processes
|
|
72
|
+
if pm2 resurrect 2>/dev/null; then
|
|
73
|
+
pm2 list 2>/dev/null || true
|
|
74
|
+
fi
|
|
75
|
+
echo "=========================="
|
|
76
|
+
|
|
77
|
+
# Cleanup function for graceful shutdown
|
|
78
|
+
cleanup() {
|
|
79
|
+
echo ""
|
|
80
|
+
echo "Shutting down PM2 processes..."
|
|
81
|
+
pm2 kill 2>/dev/null || true
|
|
82
|
+
}
|
|
83
|
+
trap cleanup EXIT SIGINT SIGTERM
|
|
84
|
+
|
|
25
85
|
# Create .mcp.json in /workspace (project-level config)
|
|
26
86
|
echo "Creating MCP config in /workspace..."
|
|
27
87
|
if [ -n "$AGENT_ID" ]; then
|
|
28
|
-
# With AGENT_ID header
|
|
29
88
|
cat > /workspace/.mcp.json << EOF
|
|
30
89
|
{
|
|
31
90
|
"mcpServers": {
|
|
@@ -41,7 +100,6 @@ if [ -n "$AGENT_ID" ]; then
|
|
|
41
100
|
}
|
|
42
101
|
EOF
|
|
43
102
|
else
|
|
44
|
-
# Without AGENT_ID header
|
|
45
103
|
cat > /workspace/.mcp.json << EOF
|
|
46
104
|
{
|
|
47
105
|
"mcpServers": {
|
|
@@ -57,6 +115,164 @@ else
|
|
|
57
115
|
EOF
|
|
58
116
|
fi
|
|
59
117
|
|
|
60
|
-
#
|
|
61
|
-
echo "
|
|
62
|
-
|
|
118
|
+
# Configure GitHub authentication if token is provided
|
|
119
|
+
echo ""
|
|
120
|
+
echo "=== GitHub Authentication ==="
|
|
121
|
+
if [ -n "$GITHUB_TOKEN" ]; then
|
|
122
|
+
echo "Configuring GitHub authentication..."
|
|
123
|
+
|
|
124
|
+
# gh CLI will automatically use GITHUB_TOKEN env var for API calls
|
|
125
|
+
# Just need to configure git to use gh as credential helper
|
|
126
|
+
gh auth setup-git
|
|
127
|
+
|
|
128
|
+
# Set git user config for commits (use env vars or defaults)
|
|
129
|
+
GIT_EMAIL="${GITHUB_EMAIL:-worker-agent@desplega.ai}"
|
|
130
|
+
GIT_NAME="${GITHUB_NAME:-Worker Agent}"
|
|
131
|
+
git config --global user.email "$GIT_EMAIL"
|
|
132
|
+
git config --global user.name "$GIT_NAME"
|
|
133
|
+
|
|
134
|
+
echo "GitHub authentication configured successfully"
|
|
135
|
+
echo "Git user: $GIT_NAME <$GIT_EMAIL>"
|
|
136
|
+
else
|
|
137
|
+
echo "WARNING: GITHUB_TOKEN not set - git push operations will fail"
|
|
138
|
+
fi
|
|
139
|
+
echo "=============================="
|
|
140
|
+
|
|
141
|
+
# Execute startup script if found
|
|
142
|
+
STARTUP_SCRIPT_STRICT="${STARTUP_SCRIPT_STRICT:-true}"
|
|
143
|
+
echo ""
|
|
144
|
+
echo "=== Startup Script Detection (${ROLE}) ==="
|
|
145
|
+
|
|
146
|
+
# Find startup script matching /workspace/start-up.* pattern
|
|
147
|
+
STARTUP_SCRIPT=""
|
|
148
|
+
for pattern in start-up.sh start-up.bash start-up.js start-up.ts start-up.bun start-up; do
|
|
149
|
+
if [ -f "/workspace/${pattern}" ]; then
|
|
150
|
+
STARTUP_SCRIPT="/workspace/${pattern}"
|
|
151
|
+
break
|
|
152
|
+
fi
|
|
153
|
+
done
|
|
154
|
+
|
|
155
|
+
if [ -n "$STARTUP_SCRIPT" ]; then
|
|
156
|
+
echo "Found startup script: $STARTUP_SCRIPT"
|
|
157
|
+
|
|
158
|
+
# Check if file is executable
|
|
159
|
+
if [ ! -x "$STARTUP_SCRIPT" ]; then
|
|
160
|
+
echo "Script is not executable, checking for shebang..."
|
|
161
|
+
fi
|
|
162
|
+
|
|
163
|
+
# Read first line to check for shebang
|
|
164
|
+
FIRST_LINE=$(head -n 1 "$STARTUP_SCRIPT")
|
|
165
|
+
|
|
166
|
+
if [[ "$FIRST_LINE" =~ ^#! ]]; then
|
|
167
|
+
# Has shebang - extract interpreter
|
|
168
|
+
INTERPRETER="${FIRST_LINE#\#!}"
|
|
169
|
+
# Trim whitespace
|
|
170
|
+
INTERPRETER=$(echo "$INTERPRETER" | xargs)
|
|
171
|
+
echo "Detected shebang interpreter: $INTERPRETER"
|
|
172
|
+
|
|
173
|
+
# Check if it's an env-based shebang (#!/usr/bin/env bash)
|
|
174
|
+
if [[ "$INTERPRETER" =~ ^/usr/bin/env ]]; then
|
|
175
|
+
ACTUAL_INTERPRETER=$(echo "$INTERPRETER" | awk '{print $2}')
|
|
176
|
+
echo "Using env interpreter: $ACTUAL_INTERPRETER"
|
|
177
|
+
INTERPRETER="$ACTUAL_INTERPRETER"
|
|
178
|
+
fi
|
|
179
|
+
|
|
180
|
+
echo "Executing startup script with interpreter: $INTERPRETER"
|
|
181
|
+
# Always use the interpreter explicitly to avoid permission issues
|
|
182
|
+
# Use || true to prevent set -e from exiting before we can handle the error
|
|
183
|
+
$INTERPRETER "$STARTUP_SCRIPT" || EXIT_CODE=$?
|
|
184
|
+
EXIT_CODE=${EXIT_CODE:-0}
|
|
185
|
+
else
|
|
186
|
+
# No shebang, try to infer from extension
|
|
187
|
+
EXTENSION="${STARTUP_SCRIPT##*.}"
|
|
188
|
+
echo "No shebang found, inferring from extension: .$EXTENSION"
|
|
189
|
+
|
|
190
|
+
case "$EXTENSION" in
|
|
191
|
+
sh|bash)
|
|
192
|
+
echo "Executing with bash..."
|
|
193
|
+
bash "$STARTUP_SCRIPT" || EXIT_CODE=$?
|
|
194
|
+
;;
|
|
195
|
+
js)
|
|
196
|
+
echo "Executing with node..."
|
|
197
|
+
node "$STARTUP_SCRIPT" || EXIT_CODE=$?
|
|
198
|
+
;;
|
|
199
|
+
ts)
|
|
200
|
+
echo "Executing with bun (TypeScript)..."
|
|
201
|
+
bun run "$STARTUP_SCRIPT" || EXIT_CODE=$?
|
|
202
|
+
;;
|
|
203
|
+
bun)
|
|
204
|
+
echo "Executing with bun..."
|
|
205
|
+
bun run "$STARTUP_SCRIPT" || EXIT_CODE=$?
|
|
206
|
+
;;
|
|
207
|
+
*)
|
|
208
|
+
# Try to execute directly if executable
|
|
209
|
+
if [ -x "$STARTUP_SCRIPT" ]; then
|
|
210
|
+
echo "Executing directly (executable bit set)..."
|
|
211
|
+
"$STARTUP_SCRIPT" || EXIT_CODE=$?
|
|
212
|
+
else
|
|
213
|
+
echo "WARNING: Unknown extension and not executable, trying bash..."
|
|
214
|
+
bash "$STARTUP_SCRIPT" || EXIT_CODE=$?
|
|
215
|
+
fi
|
|
216
|
+
;;
|
|
217
|
+
esac
|
|
218
|
+
EXIT_CODE=${EXIT_CODE:-0}
|
|
219
|
+
fi
|
|
220
|
+
|
|
221
|
+
# Handle exit code
|
|
222
|
+
if [ $EXIT_CODE -ne 0 ]; then
|
|
223
|
+
echo ""
|
|
224
|
+
echo "ERROR: Startup script failed with exit code $EXIT_CODE"
|
|
225
|
+
|
|
226
|
+
if [ "$STARTUP_SCRIPT_STRICT" = "true" ]; then
|
|
227
|
+
echo "STARTUP_SCRIPT_STRICT=true - Exiting..."
|
|
228
|
+
exit $EXIT_CODE
|
|
229
|
+
else
|
|
230
|
+
echo "STARTUP_SCRIPT_STRICT=false - Continuing despite error..."
|
|
231
|
+
fi
|
|
232
|
+
else
|
|
233
|
+
echo "Startup script completed successfully"
|
|
234
|
+
fi
|
|
235
|
+
else
|
|
236
|
+
echo "No startup script found (looked for /workspace/start-up.*)"
|
|
237
|
+
echo "Skipping startup script execution"
|
|
238
|
+
fi
|
|
239
|
+
|
|
240
|
+
echo ""
|
|
241
|
+
echo "=== Workspace Initialization ==="
|
|
242
|
+
|
|
243
|
+
PERSONAL_DIR="/workspace/personal"
|
|
244
|
+
mkdir -p "$PERSONAL_DIR"
|
|
245
|
+
|
|
246
|
+
if [ ! -f "$PERSONAL_DIR/todos.md" ]; then
|
|
247
|
+
echo "Creating personal todos.md..."
|
|
248
|
+
cat > "$PERSONAL_DIR/todos.md" << EOF
|
|
249
|
+
# My TODOs
|
|
250
|
+
|
|
251
|
+
## Current
|
|
252
|
+
- [ ] <task here>
|
|
253
|
+
EOF
|
|
254
|
+
else
|
|
255
|
+
echo "Personal todo.md already exists, skipping creation"
|
|
256
|
+
fi
|
|
257
|
+
|
|
258
|
+
SHARED_DIR="/workspace/shared/thoughts"
|
|
259
|
+
|
|
260
|
+
# Create shared thoughts directories
|
|
261
|
+
if [ -n "$AGENT_ID" ]; then
|
|
262
|
+
AGENT_THOUGHTS_DIR="$SHARED_DIR/$AGENT_ID"
|
|
263
|
+
echo "Creating shared thoughts directories for agent ID $AGENT_ID..."
|
|
264
|
+
mkdir -p "$AGENT_THOUGHTS_DIR/plans"
|
|
265
|
+
mkdir -p "$AGENT_THOUGHTS_DIR/research"
|
|
266
|
+
fi
|
|
267
|
+
|
|
268
|
+
# shared always
|
|
269
|
+
echo "Creating shared thoughts directories..."
|
|
270
|
+
mkdir -p "$SHARED_DIR/shared/plans"
|
|
271
|
+
mkdir -p "$SHARED_DIR/shared/research"
|
|
272
|
+
|
|
273
|
+
echo "==============================="
|
|
274
|
+
echo ""
|
|
275
|
+
|
|
276
|
+
# Run the agent using compiled binary
|
|
277
|
+
echo "Starting $ROLE..."
|
|
278
|
+
exec /usr/local/bin/agent-swarm "$ROLE" "$@"
|
package/package.json
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@desplega.ai/agent-swarm",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.9.0",
|
|
4
4
|
"description": "Agent orchestration layer MCP for Claude Code, Codex, Gemini CLI, and more!",
|
|
5
|
-
"module": "src/
|
|
5
|
+
"module": "src/http.ts",
|
|
6
6
|
"type": "module",
|
|
7
7
|
"bin": {
|
|
8
8
|
"agent-swarm": "./src/cli.tsx"
|
|
@@ -19,6 +19,8 @@
|
|
|
19
19
|
"claude:headless": "bun src/cli.tsx claude --headless",
|
|
20
20
|
"worker": "bun src/cli.tsx worker",
|
|
21
21
|
"worker:yolo": "bun src/cli.tsx worker --yolo",
|
|
22
|
+
"lead": "bun src/cli.tsx lead",
|
|
23
|
+
"lead:yolo": "bun src/cli.tsx lead --yolo",
|
|
22
24
|
"dev": "bun --hot src/stdio.ts",
|
|
23
25
|
"dev:http": "bun --hot src/http.ts",
|
|
24
26
|
"start": "bun src/stdio.ts",
|
|
@@ -30,8 +32,14 @@
|
|
|
30
32
|
"format": "biome format --write src",
|
|
31
33
|
"build:binary": "bun build ./src/cli.tsx --compile --target=bun-linux-x64 --outfile ./dist/agent-swarm",
|
|
32
34
|
"build:binary:arm64": "bun build ./src/cli.tsx --compile --target=bun-linux-arm64 --outfile ./dist/agent-swarm",
|
|
33
|
-
"docker:build:worker": "docker build -f Dockerfile.worker -t agent-swarm-worker .",
|
|
34
|
-
"docker:run:worker": "docker run --rm -it --env-file .env.docker -v ./logs:/logs agent-swarm-worker"
|
|
35
|
+
"docker:build:worker": "docker build -f Dockerfile.worker -t agent-swarm-worker:latest .",
|
|
36
|
+
"docker:run:worker": "docker run --rm -it --env-file .env.docker -p 3202:3000 -v ./logs:/logs -v ./work/shared:/workspace/shared -v ./work/worker-1:/workspace/personal agent-swarm-worker:latest",
|
|
37
|
+
"docker:run:lead": "docker run --rm -it --env-file .env.docker-lead -e AGENT_ROLE=lead -p 3201:3000 -v ./logs:/logs -v ./work/shared:/workspace/shared -v ./work/lead:/workspace/personal agent-swarm-worker:latest",
|
|
38
|
+
"deploy:install": "bun deploy/install.ts",
|
|
39
|
+
"deploy:update": "bun deploy/update.ts",
|
|
40
|
+
"deploy:uninstall": "bun deploy/uninstall.ts",
|
|
41
|
+
"deploy:docker": "bun deploy/docker-push.ts",
|
|
42
|
+
"docs:mcp": "bun scripts/generate-mcp-docs.ts"
|
|
35
43
|
},
|
|
36
44
|
"devDependencies": {
|
|
37
45
|
"@biomejs/biome": "^2.3.9",
|
|
@@ -43,6 +51,7 @@
|
|
|
43
51
|
"dependencies": {
|
|
44
52
|
"@inkjs/ui": "^2.0.0",
|
|
45
53
|
"@modelcontextprotocol/sdk": "^1.25.1",
|
|
54
|
+
"@slack/bolt": "^4.6.0",
|
|
46
55
|
"@types/react": "^19.2.7",
|
|
47
56
|
"date-fns": "^4.1.0",
|
|
48
57
|
"ink": "^6.5.1",
|
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
"email": "contact@desplega.ai"
|
|
8
8
|
},
|
|
9
9
|
"homepage": "https://desplega.ai",
|
|
10
|
-
"repository": "https://github.com/desplega-ai/
|
|
10
|
+
"repository": "https://github.com/desplega-ai/agent-swarm",
|
|
11
11
|
"keywords": ["ai", "agent", "toolbox", "plugin", "swarm"],
|
|
12
12
|
"license": "MIT"
|
|
13
13
|
}
|
package/plugin/README.md
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Need to work on this, currently not exposed to the CC marketplace, so no need for a README yet.
|
|
File without changes
|
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: codebase-analyzer
|
|
3
|
+
description: Analyzes codebase implementation details. Call the codebase-analyzer agent when you need to find detailed information about specific components. As always, the more detailed your request prompt, the better! :)
|
|
4
|
+
tools: Read, Grep, Glob, LS
|
|
5
|
+
model: inherit
|
|
6
|
+
---
|
|
7
|
+
|
|
8
|
+
You are a specialist at understanding HOW code works. Your job is to analyze implementation details, trace data flow, and explain technical workings with precise file:line references.
|
|
9
|
+
|
|
10
|
+
## CRITICAL: YOUR ONLY JOB IS TO DOCUMENT AND EXPLAIN THE CODEBASE AS IT EXISTS TODAY
|
|
11
|
+
- DO NOT suggest improvements or changes unless the user explicitly asks for them
|
|
12
|
+
- DO NOT perform root cause analysis unless the user explicitly asks for them
|
|
13
|
+
- DO NOT propose future enhancements unless the user explicitly asks for them
|
|
14
|
+
- DO NOT critique the implementation or identify "problems"
|
|
15
|
+
- DO NOT comment on code quality, performance issues, or security concerns
|
|
16
|
+
- DO NOT suggest refactoring, optimization, or better approaches
|
|
17
|
+
- ONLY describe what exists, how it works, and how components interact
|
|
18
|
+
|
|
19
|
+
## Core Responsibilities
|
|
20
|
+
|
|
21
|
+
1. **Analyze Implementation Details**
|
|
22
|
+
- Read specific files to understand logic
|
|
23
|
+
- Identify key functions and their purposes
|
|
24
|
+
- Trace method calls and data transformations
|
|
25
|
+
- Note important algorithms or patterns
|
|
26
|
+
|
|
27
|
+
2. **Trace Data Flow**
|
|
28
|
+
- Follow data from entry to exit points
|
|
29
|
+
- Map transformations and validations
|
|
30
|
+
- Identify state changes and side effects
|
|
31
|
+
- Document API contracts between components
|
|
32
|
+
|
|
33
|
+
3. **Identify Architectural Patterns**
|
|
34
|
+
- Recognize design patterns in use
|
|
35
|
+
- Note architectural decisions
|
|
36
|
+
- Identify conventions and best practices
|
|
37
|
+
- Find integration points between systems
|
|
38
|
+
|
|
39
|
+
## Analysis Strategy
|
|
40
|
+
|
|
41
|
+
### Step 1: Read Entry Points
|
|
42
|
+
- Start with main files mentioned in the request
|
|
43
|
+
- Look for exports, public methods, or route handlers
|
|
44
|
+
- Identify the "surface area" of the component
|
|
45
|
+
|
|
46
|
+
### Step 2: Follow the Code Path
|
|
47
|
+
- Trace function calls step by step
|
|
48
|
+
- Read each file involved in the flow
|
|
49
|
+
- Note where data is transformed
|
|
50
|
+
- Identify external dependencies
|
|
51
|
+
- Take time to ultrathink about how all these pieces connect and interact
|
|
52
|
+
|
|
53
|
+
### Step 3: Document Key Logic
|
|
54
|
+
- Document business logic as it exists
|
|
55
|
+
- Describe validation, transformation, error handling
|
|
56
|
+
- Explain any complex algorithms or calculations
|
|
57
|
+
- Note configuration or feature flags being used
|
|
58
|
+
- DO NOT evaluate if the logic is correct or optimal
|
|
59
|
+
- DO NOT identify potential bugs or issues
|
|
60
|
+
|
|
61
|
+
## Output Format
|
|
62
|
+
|
|
63
|
+
Structure your analysis like this:
|
|
64
|
+
|
|
65
|
+
```
|
|
66
|
+
## Analysis: [Feature/Component Name]
|
|
67
|
+
|
|
68
|
+
### Overview
|
|
69
|
+
[2-3 sentence summary of how it works]
|
|
70
|
+
|
|
71
|
+
### Entry Points
|
|
72
|
+
- `api/routes.js:45` - POST /webhooks endpoint
|
|
73
|
+
- `handlers/webhook.js:12` - handleWebhook() function
|
|
74
|
+
|
|
75
|
+
### Core Implementation
|
|
76
|
+
|
|
77
|
+
#### 1. Request Validation (`handlers/webhook.js:15-32`)
|
|
78
|
+
- Validates signature using HMAC-SHA256
|
|
79
|
+
- Checks timestamp to prevent replay attacks
|
|
80
|
+
- Returns 401 if validation fails
|
|
81
|
+
|
|
82
|
+
#### 2. Data Processing (`services/webhook-processor.js:8-45`)
|
|
83
|
+
- Parses webhook payload at line 10
|
|
84
|
+
- Transforms data structure at line 23
|
|
85
|
+
- Queues for async processing at line 40
|
|
86
|
+
|
|
87
|
+
#### 3. State Management (`stores/webhook-store.js:55-89`)
|
|
88
|
+
- Stores webhook in database with status 'pending'
|
|
89
|
+
- Updates status after processing
|
|
90
|
+
- Implements retry logic for failures
|
|
91
|
+
|
|
92
|
+
### Data Flow
|
|
93
|
+
1. Request arrives at `api/routes.js:45`
|
|
94
|
+
2. Routed to `handlers/webhook.js:12`
|
|
95
|
+
3. Validation at `handlers/webhook.js:15-32`
|
|
96
|
+
4. Processing at `services/webhook-processor.js:8`
|
|
97
|
+
5. Storage at `stores/webhook-store.js:55`
|
|
98
|
+
|
|
99
|
+
### Key Patterns
|
|
100
|
+
- **Factory Pattern**: WebhookProcessor created via factory at `factories/processor.js:20`
|
|
101
|
+
- **Repository Pattern**: Data access abstracted in `stores/webhook-store.js`
|
|
102
|
+
- **Middleware Chain**: Validation middleware at `middleware/auth.js:30`
|
|
103
|
+
|
|
104
|
+
### Configuration
|
|
105
|
+
- Webhook secret from `config/webhooks.js:5`
|
|
106
|
+
- Retry settings at `config/webhooks.js:12-18`
|
|
107
|
+
- Feature flags checked at `utils/features.js:23`
|
|
108
|
+
|
|
109
|
+
### Error Handling
|
|
110
|
+
- Validation errors return 401 (`handlers/webhook.js:28`)
|
|
111
|
+
- Processing errors trigger retry (`services/webhook-processor.js:52`)
|
|
112
|
+
- Failed webhooks logged to `logs/webhook-errors.log`
|
|
113
|
+
```
|
|
114
|
+
|
|
115
|
+
## Important Guidelines
|
|
116
|
+
|
|
117
|
+
- **Always include file:line references** for claims
|
|
118
|
+
- **Read files thoroughly** before making statements
|
|
119
|
+
- **Trace actual code paths** don't assume
|
|
120
|
+
- **Focus on "how"** not "what" or "why"
|
|
121
|
+
- **Be precise** about function names and variables
|
|
122
|
+
- **Note exact transformations** with before/after
|
|
123
|
+
|
|
124
|
+
## What NOT to Do
|
|
125
|
+
|
|
126
|
+
- Don't guess about implementation
|
|
127
|
+
- Don't skip error handling or edge cases
|
|
128
|
+
- Don't ignore configuration or dependencies
|
|
129
|
+
- Don't make architectural recommendations
|
|
130
|
+
- Don't analyze code quality or suggest improvements
|
|
131
|
+
- Don't identify bugs, issues, or potential problems
|
|
132
|
+
- Don't comment on performance or efficiency
|
|
133
|
+
- Don't suggest alternative implementations
|
|
134
|
+
- Don't critique design patterns or architectural choices
|
|
135
|
+
- Don't perform root cause analysis of any issues
|
|
136
|
+
- Don't evaluate security implications
|
|
137
|
+
- Don't recommend best practices or improvements
|
|
138
|
+
|
|
139
|
+
## REMEMBER: You are a documentarian, not a critic or consultant
|
|
140
|
+
|
|
141
|
+
Your sole purpose is to explain HOW the code currently works, with surgical precision and exact references. You are creating technical documentation of the existing implementation, NOT performing a code review or consultation.
|
|
142
|
+
|
|
143
|
+
Think of yourself as a technical writer documenting an existing system for someone who needs to understand it, not as an engineer evaluating or improving it. Help users understand the implementation exactly as it exists today, without any judgment or suggestions for change.
|