Commit Graph
29 Commits
Author SHA1 Message Date
asepharyana ae5356a4ea fix(health-check): read key from on-disk file first, no BWS dependency
Root cause: health-check binary runs inside a Nix venv that doesn't have
/usr/local/bin/bws on PATH. When the shell wrapper's BWS_ACCESS_TOKEN
export fails (e.g. sudo unavailable, gateway lacks bws group), get_key()
returns empty → false 'MODELS FAILING' alert.

Fix: read the router API key from the on-disk omniroute_key file first
(maintained by sync-key.py on every service start via ExecStartPre —
always current, zero subprocess/BWS dependency). Fall back to BWS CLI
only if the file is missing/stale.

Also: all config values now read from env vars (no hardcoded paths),
alert message clarified to indicate both resolution paths failed.
2026-09-09 21:05:10 +07:00
asepharyana 33928c78f5 feat: add dependabot config (npm) 2026-08-25 18:13:08 +07:00
asepharyana 31f009bb89 fix: monkey-patch litellm acompletion timeout 600s for 9router review diffs
PR-Agent Dynaconf envvar_prefix=False -> ai_timeout=120 default, PR_AGENT_AI_TIMEOUT ignored.
monkey-patch acompletion() to clamp timeout<=120 -> 600 (9router needs ~15min for 15k-token diffs).
Removed ATLAS from fallback (9router rejects provider prefixes; ATLAS needs prefix).
litellm 1.96.2 -> 1.98.0 in /opt venv (fixes 'content' KeyError on 9router Anthropic resp).
Review verified: bot posted full PR Reviewer Guide to GMW PR #1.
2026-08-25 17:10:41 +07:00
asepharyana c26ef2bf71 chore: pin systemd unit to /opt run_server.py + LD_LIBRARY_PATH
Patched run_server.py (ANTHROPIC_API_* routing for 9router, bare claude-opus-5)
lives in /opt. Nix venv (h4bkq...) reused but execs /opt/run_server.py.
LD_LIBRARY_PATH needed for libstdc++ (litellm tokenizers crate).
2026-08-25 14:54:07 +07:00
asepharyana 13156e76a5 fix: route litellm via ANTHROPIC_API_* for 9router (no openai/ prefix)
9router/omniroute reject all provider prefixes (openai/claude-* -> 404).
Model must be bare (claude-opus-5). litellm routes bare claude-* to the
Anthropic native provider, so we set ANTHROPIC_API_BASE/ANTHROPIC_API_KEY
env vars pointing at 9router instead of the OpenAI-shaped OPENAI__* env.
2026-08-25 14:24:04 +07:00
asepharyana 889a8d0a8d fix: use 9router-compatible model names (claude-opus-5, no openai/ prefix)
Bug: PR-Agent auto-review gagal karena model 'openai/claude-opus-4-8'
tidak valid di 9router (provider openai/ tidak ada).

Root cause: BWS secret pr_agent_pr_agent_model berisi prefix openai/
yang hanya valid untuk omniroute, bukan 9router. 9router pakai model
tanpa provider prefix (e.g. claude-opus-5).

Fix:
- Default CONFIG__MODEL: openai/claude-opus-5 -> claude-opus-5
- Fallback claude-sonnet-5 -> claude-sonnet-5 (drop openai/ prefix)

BWS secret juga sudah diupdate di production.
2026-08-25 14:16:35 +07:00
asepharyana bc8e1739e9 refactor: restructure into proper project layout + improve docs
Project layout:
- src/: application modules (run_server, auto_merge_bot, health-check, sync-key, trivial_merge, callback_server, start_server)
- scripts/: setup/deployment helpers (setup_all, setup_app, generate_manifest)
- templates/: manifest.json (GitHub App manifest template)
- docs/  + CONTRIBUTING.md: documentation

Improvements:
- flake.nix: added pr-agent-auto-merge wrapper binary, updated installPhase paths
- deploy.yml: syntax check covers all modules including health-check.py and sync-key.py
- README.md: comprehensive with architecture, layout, dev, ops, deployment
- CONTRIBUTING.md: standards and testing checklist
- .gitignore: added *.log, *.pid, .env.*
- Cleanup: removed duplicate manifest_current.json / manifest_final.json
- Fix: health-check.py docstring updated to claude-opus-5

Verification:
- ✅ python3 -m py_compile: all 11 modules pass
- ✅ nix flake check: passes
2026-08-20 11:38:24 +07:00
asepharyana 017656d97b feat: update models to claude-opus-5/sonnet-5/haiku-4-5-20251001 (tested live on 9router)
- PRIMARY: openai/claude-opus-5 (was openai/claude-opus-4-8)
- FALLBACKS: added openai/claude-sonnet-5, openai/claude-haiku-4-5-20251001
- Verified all three return valid responses via raw HTTP to 9router
- Updated run_server.py, health-check.py, setup_all.py
2026-08-20 11:30:10 +07:00
asepharyana 54cec6bf0c improve: add README, .editorconfig, fix fallback models in setup_all.py, update .gitignore 2026-08-20 11:26:03 +07:00
asepharyana 2293428421 fix: health watchdog false 504s — Caddy header timeout + per-model logic
Root cause: 9router combo models (deepseek-v4-flash-free on fallback) have
TTFT up to 30-40s. Caddy 9router route inherited the default
response_header_timeout 30s / read_timeout 60s → 504 'timeout awaiting
response headers' even though 9router was still processing. Cloudflare/log
showed repeated 504s; health watchdog (correctly) flagged the outage.

Fixes:
1. Caddy: dedicated 9router route with response_header_timeout 120s +
   read/write 300s (was default 30/60). Removed invalid top-level
   flush_interval on upload block that broke caddy reload (2.11 rejects it as
   transport subdirective).
2. health-check: HTTP timeout 60→150s (mirror Caddy), and alert ONLY when
   EVERY model fails — any working model means the server's fallback chain
   succeeds. Early-exit on first success to bound runtime (~3s healthy).
Verified: 3 runs green, ~3.6s each, silent exit 0.
2026-08-04 21:06:54 +07:00
asepharyana bd3d739250 ci: add Nix GC cleanup job on VPS after deploy 2026-08-04 13:57:47 +07:00
asepharyana 875ddfcca9 fix: health-check BWS token read as non-root cron user
Cron runs as user code (not root). /etc/bws-token is root:bws 640, so direct
read fails with Permission denied → watchdog exited 1 every run. Fix:
- wrapper uses sudo -n cat (code is in sudo group, NOPASSWD)
- health-check.py get_key() falls back to sudo -n cat too
Verified as code user: silent exit 0 when healthy.
2026-08-04 12:12:42 +07:00
asepharyana 407819b647 fix: parse PR-Agent analytics record-wrapped JSON format
Real PR-Agent analytics logs wrap fields under 'record': {...}. The parser
now unwraps that before extracting command/pr_url/message/level, so
/api/analytics and /api/metrics show real data (verified with actual format
from production logs).
2026-08-04 11:43:13 +07:00
asepharyana efb99b73b7 chore: gitignore nix result symlink 2026-08-04 11:39:34 +07:00
asepharyana 690f96aacb feat: add health watchdog, key auto-sync, analytics, Discord notifications, trivial-PR merge
- health-check.py: model health watchdog (silent when healthy, alert on 2+
  consecutive failures) — catches stale-key/model-breakage like 2026-08-04
- sync-key.py: systemd ExecStartPre syncs 9router key from BWS to disk,
  prevents silent 401s after key rotation
- run_server.py: CONFIG__ANALYTICS_FOLDER + /api/metrics (Prometheus) +
  /api/analytics (JSON) + /api/v1/notify_review (Discord webhook)
- trivial_merge.py: trivial-PR fast-path (docs/deps/tiny diffs) approve+merge
- auto_merge_bot.py: Discord notifications on merge, trivial integration
- flake.nix: ship pr-agent-sync-key + pr-agent-health-check binaries
2026-08-04 11:39:29 +07:00
asepharyana 06f3314819 fix: replace broken openai/auto fallback models with working 9router aliases
openai/auto/best-coding and openai/auto/claude-sonnet return
'No active credentials for provider: auto' on 9router (broken upstream
key). Primary openai/claude-opus-4-8 + fallbacks now all verified
working via litellm against 9router.asepharyana.my.id.
2026-08-04 10:17:29 +07:00
aseph ca67f0328b ci: use free GHA Nix cache (disable FlakeHub cache, not subscribed) 2026-08-03 16:44:18 +07:00
asepharyana fa0e031ba9 ci: enable FlakeHub Cache (id-token: write + use-flakehub) 2026-08-03 16:22:48 +07:00
asepharyana e0e591a63c fix: unterminated triple-quote in setup_all.py secrets template 2026-08-03 13:39:36 +07:00
asepharyana eb97e020dd ci: add python syntax-check gate before Nix deploy 2026-08-03 13:37:29 +07:00
asepharyana 86ff584b15 chore: webhook URLs to domain, manifest.json sync 2026-08-02 16:22:32 +07:00
asepharyana b9ba5ad9fa chore: use domain for webhook URLs 2026-08-02 16:21:47 +07:00
asepharyana 637b44a9e0 chore: port 3000 to 4002, use domain instead of IP 2026-08-02 16:15:43 +07:00
asepharyana 081b2ad4b5 fix(nix): restrict flake to x86_64-linux (nixpkgs 26.11 dropped darwin) 2026-08-01 18:03:43 +07:00
asepharyana eadc674565 ci: publish flake to FlakeHub (rolling) 2026-08-01 17:58:21 +07:00
asepharyana 18cf0d26aa ci: migrate CI to GitHub Actions (deploy nix + mirror ke Gitea backup)
Mirror to Gitea / mirror (push) Successful in 9s
Build & Deploy (Nix) / build-and-deploy (push) Failing after 32m50s
2026-08-01 16:41:46 +07:00
MythEclipse 7ae7b6662d fix(ci): robust SSH key handling (base64/raw) + validation
Build & Deploy (Nix) / build-and-deploy (push) Successful in 2m24s
2026-07-31 09:58:37 +07:00
MythEclipse 09ed866525 fix(nix): add libstdc++ for tokenizers native dep
Build & Deploy (Nix) / build-and-deploy (push) Successful in 2m21s
2026-07-31 09:43:10 +07:00
MythEclipse 163a1ef7ab feat: PR-Agent GitHub App server — sanitized source + Nix flake + CI deploy 2026-07-31 09:35:03 +07:00