Claude Code Claude Opus 4.6 commited on
Commit
de5ce91
·
1 Parent(s): ccc6c75

Claude Code: Add global exception handler and better startup logging for health check debugging

Browse files

- Add global exception handler to catch all unhandled errors
- Add try/except around app initialization with proper exit on failure
- Add flush=True to all startup prints for immediate log output
- Add service name to root endpoint response
- Add shutdown event handler for cleaner logs
- Log full tracebacks for debugging

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

Files changed (1) hide show
  1. app.py +34 -10
app.py CHANGED
@@ -6,20 +6,23 @@ FastAPI with lazy imports to avoid startup blocking.
6
  import os
7
  import sys
8
  import time
 
9
 
10
  # EXPLICIT STARTUP PRINTS (visible in container logs)
11
- print(">>> CAIN: Python app.py loading...")
12
- print(">>> CAIN: Python version:", sys.version.split()[0])
13
- print(">>> CAIN: Working directory:", os.getcwd())
14
- print(">>> CAIN: PORT =", os.environ.get('PORT', '7860'))
15
- print(">>> CAIN: sys.stdout flush...", flush=True)
16
 
17
  # Lazy import FastAPI to avoid blocking init
18
  def get_app():
19
  """Create FastAPI app with imports inside function."""
20
- from fastapi import FastAPI
 
21
  import logging
22
 
 
 
23
  # Configure stdout logging
24
  logging.basicConfig(
25
  level=logging.INFO,
@@ -27,8 +30,6 @@ def get_app():
27
  handlers=[logging.StreamHandler(sys.stdout)]
28
  )
29
  logger = logging.getLogger(__name__)
30
-
31
- print(">>> CAIN: Creating FastAPI app...", flush=True)
32
  logger.info(">>> CAIN: FastAPI initialization starting")
33
 
34
  app = FastAPI(title="HuggingClaw - Cain", version="0.0.1")
@@ -38,25 +39,48 @@ def get_app():
38
  @app.get("/")
39
  async def root():
40
  """Root endpoint - simple alive status."""
41
- return {"status": "alive"}
42
 
43
  @app.get("/health")
44
  async def health():
45
  """Health check endpoint for external monitoring."""
46
  return {"status": "healthy", "uptime": round(time.time() - START_TIME, 2)}
47
 
 
 
 
 
 
 
 
 
 
 
48
  @app.on_event("startup")
49
  async def startup():
50
  """Log startup complete."""
51
  print(">>> CAIN: Startup complete - ready to serve", flush=True)
52
  logger.info(">>> CAIN: Ready to serve requests on port %s", os.environ.get('PORT', '7860'))
53
 
 
 
 
 
 
 
54
  print(">>> CAIN: FastAPI app created successfully", flush=True)
55
  return app
56
 
57
 
58
  # Create app at module level for uvicorn
59
- app = get_app()
 
 
 
 
 
 
 
60
 
61
 
62
  if __name__ == "__main__":
 
6
  import os
7
  import sys
8
  import time
9
+ import traceback
10
 
11
  # EXPLICIT STARTUP PRINTS (visible in container logs)
12
+ print(">>> CAIN: Python app.py loading...", flush=True)
13
+ print(">>> CAIN: Python version:", sys.version.split()[0], flush=True)
14
+ print(">>> CAIN: Working directory:", os.getcwd(), flush=True)
15
+ print(">>> CAIN: PORT =", os.environ.get('PORT', '7860'), flush=True)
 
16
 
17
  # Lazy import FastAPI to avoid blocking init
18
  def get_app():
19
  """Create FastAPI app with imports inside function."""
20
+ from fastapi import FastAPI, Request, HTTPException
21
+ from fastapi.responses import JSONResponse
22
  import logging
23
 
24
+ print(">>> CAIN: Creating FastAPI app...", flush=True)
25
+
26
  # Configure stdout logging
27
  logging.basicConfig(
28
  level=logging.INFO,
 
30
  handlers=[logging.StreamHandler(sys.stdout)]
31
  )
32
  logger = logging.getLogger(__name__)
 
 
33
  logger.info(">>> CAIN: FastAPI initialization starting")
34
 
35
  app = FastAPI(title="HuggingClaw - Cain", version="0.0.1")
 
39
  @app.get("/")
40
  async def root():
41
  """Root endpoint - simple alive status."""
42
+ return {"status": "alive", "service": "cain"}
43
 
44
  @app.get("/health")
45
  async def health():
46
  """Health check endpoint for external monitoring."""
47
  return {"status": "healthy", "uptime": round(time.time() - START_TIME, 2)}
48
 
49
+ @app.exception_handler(Exception)
50
+ async def global_exception_handler(request: Request, exc: Exception):
51
+ """Global exception handler to catch all errors."""
52
+ logger.error(f"Unhandled exception: {type(exc).__name__}: {str(exc)}")
53
+ logger.error(f"Traceback: {traceback.format_exc()}")
54
+ return JSONResponse(
55
+ status_code=500,
56
+ content={"error": True, "message": str(exc), "type": type(exc).__name__}
57
+ )
58
+
59
  @app.on_event("startup")
60
  async def startup():
61
  """Log startup complete."""
62
  print(">>> CAIN: Startup complete - ready to serve", flush=True)
63
  logger.info(">>> CAIN: Ready to serve requests on port %s", os.environ.get('PORT', '7860'))
64
 
65
+ @app.on_event("shutdown")
66
+ async def shutdown():
67
+ """Log shutdown."""
68
+ print(">>> CAIN: Shutdown triggered", flush=True)
69
+ logger.info(">>> CAIN: Shutting down")
70
+
71
  print(">>> CAIN: FastAPI app created successfully", flush=True)
72
  return app
73
 
74
 
75
  # Create app at module level for uvicorn
76
+ try:
77
+ print(">>> CAIN: Initializing app...", flush=True)
78
+ app = get_app()
79
+ print(">>> CAIN: App initialization complete", flush=True)
80
+ except Exception as e:
81
+ print(f">>> CAIN: FATAL - App initialization failed: {e}", flush=True)
82
+ print(f">>> CAIN: Traceback: {traceback.format_exc()}", flush=True)
83
+ sys.exit(1)
84
 
85
 
86
  if __name__ == "__main__":