SPB Git forge

spb/doc-api

Public
2commits 1branches 0releases
15.7 MBsize
maindefault branch
13 days agolast push
Python 88.3% TypeScript 7.6% Shell 4.1%
5.7 KB · 89 lines python
Raw Blame History
1#!/usr/bin/env python32"""Read-only live probes for the OpenAI admin/webhooks/errors domain.3Every call is logged to reports/live-requests.jsonl by scripts.live; sanitized bodies go to tmp-live/openai-admin/.4No destructive action. Only GET/LIST admin calls + deliberately-invalid requests (rejected before billing)5+ ONE tiny chat completion (max_tokens=5) to observe rate-limit headers.6"""7from __future__ import annotations8import json, sys, time9from pathlib import Path10ROOT = Path(__file__).resolve().parents[2]11sys.path.insert(0, str(ROOT))12from scripts import live  # noqa: E4021314OUT = ROOT / "tmp-live" / "openai-admin"15OUT.mkdir(parents=True, exist_ok=True)16now = int(time.time())17week_ago = now - 7 * 8640018summary = []1920def probe(name, method, path, *, json_body=None, data=None, content_type="application/json", extra_headers=None, note="", est=0.0):21    st, body, hdrs = live.openai_request(method, path, json_body, data=data, content_type=content_type,22                                         extra_headers=extra_headers, note=note, est_cost_usd=est)23    if isinstance(body, bytes):24        try:25            body = body.decode()26        except Exception:  # noqa: BLE00127            body = f"<{len(body)} bytes>"28    rec = {"name": name, "method": method, "path": path, "status": st,29           "headers": live.interesting_headers(hdrs), "body": body}30    live.save_sanitized(rec, OUT / f"{name}.json")31    summary.append({k: rec[k] for k in ("name", "method", "path", "status")} | {32        "error": (body.get("error") if isinstance(body, dict) else None)})33    err = body.get("error") if isinstance(body, dict) else None34    print(f"{st:>3} {method:6} {path[:70]:70} {json.dumps(err)[:160] if err else ''}")35    return st, body, hdrs3637# ---- Admin API (expect 403 Missing scopes with a project key) ----38for name, path in [39    ("admin_users", "/v1/organization/users?limit=1"),40    ("admin_invites", "/v1/organization/invites?limit=1"),41    ("admin_projects", "/v1/organization/projects?limit=1"),42    ("admin_audit_logs", "/v1/organization/audit_logs?limit=1"),43    ("admin_admin_api_keys", "/v1/organization/admin_api_keys?limit=1"),44    ("admin_usage_completions", f"/v1/organization/usage/completions?start_time={week_ago}&limit=1"),45    ("admin_costs", f"/v1/organization/costs?start_time={week_ago}&limit=1"),46    ("admin_certificates", "/v1/organization/certificates?limit=1"),47    ("admin_roles", "/v1/organization/roles?limit=1"),48    ("admin_groups", "/v1/organization/groups?limit=1"),49    ("admin_spend_limit", "/v1/organization/spend_limit"),50    ("admin_data_retention", "/v1/organization/data_retention"),51    ("admin_external_storage", "/v1/organization/external_storage"),52    ("admin_spend_alerts", "/v1/organization/spend_alerts"),53]:54    probe(name, "GET", path, note="admin probe with project key")5556# ---- Webhooks (project-scoped; may work with a normal key) ----57probe("webhook_endpoints_list", "GET", "/v1/webhook_endpoints?limit=1", note="webhook endpoints list")58probe("webhook_event_types", "GET", "/v1/webhook_event_types", note="webhook event types")5960# ---- Deliberate error shapes (all rejected before generation => free) ----61probe("err_model_not_found", "POST", "/v1/responses",62      json_body={"model": "does-not-exist-model", "input": "Reply with OK.", "max_output_tokens": 16}, note="404 model_not_found")63probe("err_invalid_type", "POST", "/v1/responses",64      json_body={"model": "gpt-5.4-nano", "input": "Reply with OK.", "max_output_tokens": "sixteen"}, note="400 invalid type")65probe("err_missing_param", "POST", "/v1/responses", json_body={"input": "Reply with OK."}, note="400 missing model")66probe("err_unknown_param", "POST", "/v1/responses",67      json_body={"model": "gpt-5.4-nano", "input": "Reply with OK.", "max_output_tokens": 16, "definitely_not_a_param": 1}, note="400 unknown parameter")68probe("err_invalid_json", "POST", "/v1/responses", data=b'{"model": "gpt-5.4-nano", "input": ', note="400 invalid JSON")69probe("err_invalid_api_key", "GET", "/v1/models", extra_headers={"Authorization": "Bearer sk-invalid"}, note="401 invalid_api_key (bogus literal)")70probe("err_no_auth", "GET", "/v1/models", extra_headers={"Authorization": ""}, note="401 missing auth")71probe("err_response_not_found", "GET", "/v1/responses/resp_000000000000000000000000000000", note="404 response id")72probe("err_invalid_url", "GET", "/v1/this_endpoint_does_not_exist", note="404 invalid URL")73probe("err_context_length", "POST", "/v1/chat/completions",74      json_body={"model": "gpt-4.1-nano", "messages": [{"role": "user", "content": "Reply with OK."}], "max_tokens": 100000000}, note="400 max_tokens too large")75probe("err_bad_content_type", "POST", "/v1/responses", data=b"model=gpt-5.4-nano", content_type="text/plain", note="400/415 content type")76probe("err_bad_org_header", "GET", "/v1/models", extra_headers={"OpenAI-Organization": "org-doesnotexist0000"}, note="401 bad org header")77probe("err_bad_project_header", "GET", "/v1/models", extra_headers={"OpenAI-Project": "proj_doesnotexist0000"}, note="bad project header")78probe("err_wrong_method", "PATCH", "/v1/models", note="405? wrong method")79probe("err_bad_client_request_id", "GET", "/v1/models", extra_headers={"X-Client-Request-Id": "é" * 10}, note="400 non-ascii X-Client-Request-Id")8081# ---- One tiny paid call to observe headers (x-ratelimit-*, x-request-id, openai-*) ----82probe("ok_chat_headers", "POST", "/v1/chat/completions",83      json_body={"model": "gpt-4.1-nano", "messages": [{"role": "user", "content": "Reply with OK."}], "max_tokens": 5},84      extra_headers={"X-Client-Request-Id": "atlas-openai-admin-headers-probe-0001"}, note="header observation", est=0.00001)85probe("ok_models_headers", "GET", "/v1/models/gpt-4.1-nano", note="header observation GET")8687live.save_sanitized(summary, OUT / "summary.json")88print("saved", OUT)89