بنقرة واحدة
dev-up
Tear down and bring up a fresh local dev environment from scratch (wipes database)
التثبيت باستخدام Codex أو Claude انسخ هذا Prompt والصقه في Codex أو Claude أو مساعد آخر ليراجع صفحة Skill ويثبّتها لك.
القائمة
Tear down and bring up a fresh local dev environment from scratch (wipes database)
التثبيت باستخدام Codex أو Claude انسخ هذا Prompt والصقه في Codex أو Claude أو مساعد آخر ليراجع صفحة Skill ويثبّتها لك.
Check for new releases, security audit changes, and deploy to OpenShift staging
Trigger the automated release pipeline for Alcove
Rebuild and restart Bridge while preserving the database and all configuration
استنادا إلى تصنيف SOC المهني
| name | dev-up |
| description | Tear down and bring up a fresh local dev environment from scratch (wipes database) |
| user-invocable | true |
Fresh dev environment from scratch. Wipes the database. Every step must succeed before proceeding.
git checkout main && git pull
make down
for c in $(podman ps -a --format "{{.Names}}" | grep -E "gate-|skiff-"); do podman rm -f "$c" 2>/dev/null; done
podman volume rm -f alcove-ledger-data
Verify the volume is gone:
podman volume ls | grep alcove
Must return empty. If not, stop and debug before continuing.
make up
Wait 5 seconds, then verify Bridge is running:
podman ps --filter name=alcove-bridge --format "{{.Names}} {{.Status}}"
Must show alcove-bridge Up. If Bridge isn't running, check logs with:
podman logs alcove-bridge 2>&1 | tail -20
If the container doesn't exist at all (--rm cleaned it up after a crash), rerun without --rm to capture logs:
VER=$(git describe --tags --always --dirty)
podman run -d --replace --name alcove-bridge \
--network alcove-internal,alcove-external -p 8080:8080 \
--user 0 --security-opt label=disable \
-v ${XDG_RUNTIME_DIR}/podman/podman.sock:/run/podman/podman.sock \
-v $(pwd)/bin/bridge:/usr/local/bin/bridge:ro,z \
-v $(pwd)/web:/web:ro,z \
$(test -f alcove.yaml && echo "-v $(pwd)/alcove.yaml:/etc/alcove/alcove.yaml:ro,z") \
-e CONTAINER_HOST=unix:///run/podman/podman.sock \
-e LEDGER_DATABASE_URL=postgres://alcove:alcove@alcove-ledger:5432/alcove?sslmode=disable \
-e HAIL_URL=nats://alcove-hail:4222 \
-e RUNTIME=podman -e ALCOVE_WEB_DIR=/web \
-e ALCOVE_NETWORK=alcove-internal -e ALCOVE_EXTERNAL_NETWORK=alcove-external \
-e SKIFF_IMAGE=localhost/alcove-skiff-base:$VER \
-e GATE_IMAGE=localhost/alcove-gate:$VER \
localhost/alcove-bridge:$VER
Wait for PostgreSQL to be ready before proceeding:
for i in $(seq 1 15); do podman exec alcove-ledger pg_isready -U alcove -q 2>/dev/null && break; sleep 1; done
Then verify health:
curl -s http://localhost:8080/api/v1/health
IMPORTANT: Steps 4-7 all use $TOKEN. They must be run in the same shell invocation (chain with &&) so the variable persists.
TOKEN=$(curl -s http://localhost:8080/api/v1/auth/login -H 'Content-Type: application/json' \
-d '{"username":"admin","password":"admin"}' | python3 -c "import sys,json; print(json.load(sys.stdin).get('token',''))")
Verify TOKEN is not empty before continuing. If empty, the Bridge may not be ready yet or the auth backend may not have seeded the admin user. Check podman logs alcove-bridge 2>&1 | tail -20.
Read .dev-credentials.yaml to determine the LLM provider and create the appropriate credential. This file is the single source of truth for developer credentials.
Run this Python script to parse .dev-credentials.yaml and create the credential via curl. The script receives the auth token via the ALCOVE_TOKEN environment variable (no temp files).
ALCOVE_TOKEN="$TOKEN" python3 -c "
import yaml, json, subprocess, os, sys
token = os.environ['ALCOVE_TOKEN']
creds_file = '.dev-credentials.yaml'
if not os.path.exists(creds_file):
print('SKIP: .dev-credentials.yaml not found.')
print('To fix: cp .dev-credentials.yaml.example .dev-credentials.yaml and fill in your values.')
sys.exit(0)
with open(creds_file) as f:
creds = yaml.safe_load(f) or {}
llm = creds.get('llm')
if not llm or not llm.get('provider'):
print('SKIP: No llm section in .dev-credentials.yaml. Sessions will not have LLM access.')
print('To fix: edit .dev-credentials.yaml and configure the llm section (see .dev-credentials.yaml.example).')
sys.exit(0)
provider = llm['provider']
if provider == 'anthropic':
payload = json.dumps({
'name': 'Anthropic',
'provider': 'anthropic',
'auth_type': 'api_key',
'credential': llm.get('api_key', ''),
})
elif provider == 'claude-oauth':
payload = json.dumps({
'name': 'Claude OAuth',
'provider': 'claude-oauth',
'auth_type': 'api_key',
'credential': llm.get('oauth_token', ''),
})
elif provider == 'google-vertex':
payload = json.dumps({
'name': 'Vertex AI',
'provider': 'google-vertex',
'auth_type': 'service_account',
'credential': llm.get('service_account_json', ''),
'project_id': llm.get('project_id', ''),
'region': llm.get('region', ''),
})
else:
print(f'ERROR: unknown llm provider: {provider}')
sys.exit(1)
r = subprocess.run(['curl', '-s', '-X', 'POST',
'http://localhost:8080/api/v1/credentials',
'-H', f'Authorization: Bearer {token}',
'-H', 'Content-Type: application/json',
'-d', payload], capture_output=True, text=True)
print(r.stdout)
if r.returncode != 0:
print(f'curl error: {r.stderr}', file=sys.stderr)
sys.exit(1)
"
Verify it was created (should print JSON with an id field, not an error). If .dev-credentials.yaml is missing or has no llm section, the script prints a SKIP message -- that is acceptable but sessions will not have LLM access until the developer configures it.
ALCOVE_TOKEN="$TOKEN" python3 -c "
import yaml, json, subprocess, os, sys
token = os.environ['ALCOVE_TOKEN']
creds_file = '.dev-credentials.yaml'
if not os.path.exists(creds_file):
print('SKIP: .dev-credentials.yaml not found. No GitHub credential created.')
print('Falling back to gh auth token...')
r = subprocess.run(['gh', 'auth', 'token'], capture_output=True, text=True)
gh_token = r.stdout.strip() if r.returncode == 0 else ''
if not gh_token:
print('SKIP: No GitHub token available. Agent repo sync will not work.')
sys.exit(0)
else:
with open(creds_file) as f:
creds = yaml.safe_load(f) or {}
gh_token = creds.get('github_token', '')
if not gh_token:
print('No github_token in .dev-credentials.yaml, falling back to gh auth token...')
r = subprocess.run(['gh', 'auth', 'token'], capture_output=True, text=True)
gh_token = r.stdout.strip() if r.returncode == 0 else ''
if not gh_token:
print('SKIP: No GitHub token available. Agent repo sync will not work.')
sys.exit(0)
payload = json.dumps({
'name': 'github',
'provider': 'github',
'auth_type': 'api_key',
'credential': gh_token,
})
r = subprocess.run(['curl', '-s', '-X', 'POST',
'http://localhost:8080/api/v1/credentials',
'-H', f'Authorization: Bearer {token}',
'-H', 'Content-Type: application/json',
'-d', payload], capture_output=True, text=True)
print(r.stdout)
if r.returncode != 0:
print(f'curl error: {r.stderr}', file=sys.stderr)
sys.exit(1)
"
Verify it was created (should print JSON with an id field, not an error).
curl -s -X PUT http://localhost:8080/api/v1/user/settings/agent-repos \
-H "Authorization: Bearer $TOKEN" -H "Content-Type: application/json" \
-d '{"repos":[{"url":"https://github.com/alcove-ai/alcove-testing.git","ref":"main","name":"alcove-testing"}]}'
Trigger sync:
curl -s -X POST http://localhost:8080/api/v1/agent-definitions/sync -H "Authorization: Bearer $TOKEN"
Verify sync succeeded:
podman logs alcove-bridge 2>&1 | grep "agent-repo-syncer: synced"
Must show "synced N agent definition(s)" with N > 0. If it shows 0 or no output, the repo URL or GitHub credential may be wrong.
Confirm credentials are configured:
curl -s -H "Authorization: Bearer $TOKEN" http://localhost:8080/api/v1/credentials
Must show at least 1 credential (GitHub). If system_llm was configured, should show 2 credentials (LLM + GitHub).
curl -s -H "Authorization: Bearer $TOKEN" http://localhost:8080/api/v1/sessions?per_page=1
Must show "total": 0 (clean database).
Now that the database is seeded with credentials and agent repos, stop the containerized Bridge and switch to the hot-reload workflow:
make down
make watch
From here on, save a .go file and Air automatically rebuilds Bridge. The database retains all credentials and agent repos. Real Skiff/Gate sessions dispatch because make watch ensures container images are built.
If postgres auth is needed instead of the default memory backend, restart Bridge with AUTH_BACKEND=postgres using the manual container command from Step 3.
Three things configured:
One thing verified:
Ongoing dev workflow: use make watch (not make up) for day-to-day development.