mikeboone Claude Fable 5 commited on
Commit
a423344
·
1 Parent(s): 9a955a5

test(mcp): retry brief fetch on network errors + --brief-file escape hatch

Browse files

Venue WiFi/proxy flaps were killing the burn-in with SSL errors before the
first build even fired. Fetch now retries 5x with backoff and fails with a
clear message; --brief-file runs the same brief from a local snapshot when
Supabase is unreachable.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>

Files changed (1) hide show
  1. tests/mcp_repeat_test.py +33 -13
tests/mcp_repeat_test.py CHANGED
@@ -43,18 +43,32 @@ def log(msg: str) -> None:
43
  print(f"[{time.strftime('%H:%M:%S')}] {msg}", flush=True)
44
 
45
 
46
- def fetch_latest_brief(company: str) -> tuple[str, str, str]:
47
- rows = (
48
- SupabaseSettings().client.table("demo_history")
49
- .select("company_name,use_case,results,created_at")
50
- .eq("status", "mcp_intake")
51
- .ilike("company_name", f"%{company}%")
52
- .order("created_at", desc=True)
53
- .limit(1)
54
- .execute()
55
- .data
56
- or []
57
- )
 
 
 
 
 
 
 
 
 
 
 
 
 
 
58
  if not rows:
59
  raise SystemExit(f"No mcp_intake brief for {company!r} in demo_history")
60
  row = rows[0]
@@ -129,6 +143,8 @@ def main() -> None:
129
  ap.add_argument("--company", default="Tixr")
130
  ap.add_argument("--owner", default="jack.rayner@thoughtspot.com")
131
  ap.add_argument("--timeout-min", type=int, default=30, help="per-run timeout")
 
 
132
  args = ap.parse_args()
133
 
134
  ep = os.getenv("MCP_ENDPOINT", H.DEFAULT_ENDPOINT)
@@ -136,7 +152,11 @@ def main() -> None:
136
  if not tok:
137
  raise SystemExit("MCP_ACCESS_TOKEN not set (env or demoprep_mcp/.env)")
138
 
139
- brief, use_case, brief_ts = fetch_latest_brief(args.company)
 
 
 
 
140
  log(f"{args.company} brief from {brief_ts} | use_case={use_case!r} | len={len(brief)}")
141
  log(f"Running {args.count}x sequentially against {ep}")
142
 
 
43
  print(f"[{time.strftime('%H:%M:%S')}] {msg}", flush=True)
44
 
45
 
46
+ def fetch_latest_brief(company: str, attempts: int = 5) -> tuple[str, str, str]:
47
+ rows = None
48
+ for attempt in range(1, attempts + 1):
49
+ try:
50
+ rows = (
51
+ SupabaseSettings().client.table("demo_history")
52
+ .select("company_name,use_case,results,created_at")
53
+ .eq("status", "mcp_intake")
54
+ .ilike("company_name", f"%{company}%")
55
+ .order("created_at", desc=True)
56
+ .limit(1)
57
+ .execute()
58
+ .data
59
+ or []
60
+ )
61
+ break
62
+ except Exception as e:
63
+ # Venue WiFi / proxy flaps surface here as SSL or connect errors;
64
+ # retry rather than dying before the first build is even fired.
65
+ if attempt == attempts:
66
+ raise SystemExit(
67
+ f"Supabase unreachable after {attempts} attempts ({type(e).__name__}: "
68
+ f"{str(e)[:160]}). Check network/proxy, or pass --brief-file."
69
+ )
70
+ log(f"brief fetch failed ({type(e).__name__}), retry {attempt}/{attempts - 1} in 10s")
71
+ time.sleep(10)
72
  if not rows:
73
  raise SystemExit(f"No mcp_intake brief for {company!r} in demo_history")
74
  row = rows[0]
 
143
  ap.add_argument("--company", default="Tixr")
144
  ap.add_argument("--owner", default="jack.rayner@thoughtspot.com")
145
  ap.add_argument("--timeout-min", type=int, default=30, help="per-run timeout")
146
+ ap.add_argument("--brief-file", help="read the brief from a local file instead of Supabase "
147
+ "(use when the network can't reach Supabase)")
148
  args = ap.parse_args()
149
 
150
  ep = os.getenv("MCP_ENDPOINT", H.DEFAULT_ENDPOINT)
 
152
  if not tok:
153
  raise SystemExit("MCP_ACCESS_TOKEN not set (env or demoprep_mcp/.env)")
154
 
155
+ if args.brief_file:
156
+ brief = open(args.brief_file).read()
157
+ use_case, brief_ts = "Event Ticketing Analytics", f"file:{args.brief_file}"
158
+ else:
159
+ brief, use_case, brief_ts = fetch_latest_brief(args.company)
160
  log(f"{args.company} brief from {brief_ts} | use_case={use_case!r} | len={len(brief)}")
161
  log(f"Running {args.count}x sequentially against {ep}")
162