Root cause: Template expects flat structure (metrics.database.count) but monitoring module provides nested structure (metrics.by_type.database.count) with different field names (avg_duration_ms vs avg). Solution: Route Adapter Pattern - transformer function maps data structure at presentation layer. Changes: - Add transform_metrics_for_template() function to admin.py - Update metrics_dashboard() route to use transformer - Provide safe defaults for missing/empty metrics data - Handle all operation types: database, http, render Testing: All 32 admin route tests passing Documentation: - Updated implementation report with actual fix details - Created consolidated hotfix design documentation - Architectural review by architect (approved with minor concerns) Technical debt: Adapter layer should be replaced with proper data contracts in v1.2.0 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
5.9 KiB
5.9 KiB
Hotfix Design: v1.1.1-rc.2 Route Conflict Resolution
Problem Summary
Production deployment of v1.1.1-rc.1 causes 500 error at /admin/dashboard due to:
- Route naming conflict between two dashboard functions
- Missing
starpunk.monitoringmodule causing ImportError
Root Cause Analysis
Primary Issue: Route Conflict
# Line 26: Original dashboard
@bp.route("/") # Registered as "admin.dashboard"
def dashboard(): # Function name creates endpoint "admin.dashboard"
# Shows notes list
# Line 218: Metrics dashboard
@bp.route("/dashboard") # CONFLICT: Also accessible at /admin/dashboard
def metrics_dashboard(): # Function name creates endpoint "admin.metrics_dashboard"
from starpunk.monitoring import get_metrics_stats # FAILS: Module doesn't exist
Secondary Issue: Missing Module
The metrics dashboard attempts to import starpunk.monitoring which doesn't exist in production, causing immediate ImportError on route access.
Solution Design
Minimal Code Changes
1. Route Path Change (admin.py)
Line 218 - Change route decorator:
# FROM:
@bp.route("/dashboard")
# TO:
@bp.route("/metrics-dashboard")
This single character change resolves the route conflict while maintaining all other functionality.
2. Defensive Import Pattern (admin.py)
Lines 239-250 - Add graceful degradation:
def metrics_dashboard():
"""Metrics visualization dashboard (Phase 3)"""
# Defensive imports with fallback
try:
from starpunk.database.pool import get_pool_stats
from starpunk.monitoring import get_metrics_stats
monitoring_available = True
except ImportError:
monitoring_available = False
get_pool_stats = lambda: {"error": "Pool stats not available"}
get_metrics_stats = lambda: {"error": "Monitoring not implemented"}
# Continue with safe execution...
URL Structure After Fix
| Path | Function | Purpose | Status |
|---|---|---|---|
/admin/ |
dashboard() |
Notes list | Working |
/admin/metrics-dashboard |
metrics_dashboard() |
Metrics viz | Fixed |
/admin/metrics |
metrics() |
JSON API | Working |
/admin/health |
health_diagnostics() |
Health check | Working |
Redirect Behavior
All existing redirects using url_for("admin.dashboard") will continue to work:
- They resolve to the
dashboard()function - Users land on the notes list at
/admin/ - No code changes needed in 8+ redirect locations
Navigation Updates
The template at /templates/admin/base.html is already correct:
<a href="{{ url_for('admin.dashboard') }}">Dashboard</a> <!-- Goes to /admin/ -->
<a href="{{ url_for('admin.metrics_dashboard') }}">Metrics</a> <!-- Goes to /admin/metrics-dashboard -->
Implementation Steps
Step 1: Create Hotfix Branch
git checkout -b hotfix/v1.1.1-rc2-route-conflict
Step 2: Apply Code Changes
- Edit
/starpunk/routes/admin.py:- Change line 218 route decorator
- Add try/except around monitoring imports (lines 239-250)
- Add try/except around pool stats import (line 284)
Step 3: Local Testing
# Test without monitoring module (production scenario)
uv run python -m pytest tests/test_admin_routes.py
uv run flask run
# Verify:
# 1. /admin/ shows notes
# 2. /admin/metrics-dashboard doesn't 500
# 3. All CRUD operations work
Step 4: Update Version
Edit /starpunk/__init__.py:
__version__ = "1.1.1-rc.2"
Step 5: Document in CHANGELOG
Add to /CHANGELOG.md:
## [1.1.1-rc.2] - 2025-11-25
### Fixed
- Critical: Resolved route conflict causing 500 error on /admin/dashboard
- Added defensive imports for missing monitoring module
- Renamed metrics dashboard route to /admin/metrics-dashboard for clarity
Testing Checklist
Functional Tests
/admin/displays notes dashboard/admin/metrics-dashboardloads without 500 error- Create note redirects to
/admin/ - Edit note redirects to
/admin/ - Delete note redirects to
/admin/ - Navigation links work correctly
/admin/metricsJSON endpoint works/admin/healthdiagnostic endpoint works
Error Handling Tests
- Metrics dashboard shows graceful message when monitoring unavailable
- No Python tracebacks exposed to users
- Flash messages display appropriately
Regression Tests
- IndieAuth login flow works
- Note CRUD operations unchanged
- RSS feed generation works
- Micropub endpoint functional
Rollback Plan
If issues discovered after deployment:
- Revert to v1.1.1-rc.1
- Users directed to
/admin/instead of/admin/dashboard - Metrics dashboard temporarily disabled
Success Criteria
- No 500 Errors: All admin routes respond with 200/300 status codes
- Backward Compatible: Existing functionality unchanged
- Clear Navigation: Users can access both dashboards
- Graceful Degradation: Missing modules handled elegantly
Long-term Recommendations
For v1.2.0
- Implement
starpunk.monitoringmodule properly - Add comprehensive metrics collection
- Consider dashboard consolidation
For v2.0.0
- Restructure admin area with sub-blueprints
- Implement consistent URL patterns
- Add dashboard customization options
Risk Assessment
| Risk | Likelihood | Impact | Mitigation |
|---|---|---|---|
| Route still conflicts | Low | High | Tested locally first |
| Template breaks | Low | Medium | Template already correct |
| Monitoring import fails differently | Low | Low | Defensive imports added |
| Performance impact | Very Low | Low | Minimal code change |
Approval Requirements
This hotfix requires:
- Code review of changes
- Local testing confirmation
- Staging deployment (if available)
- Production deployment authorization
Contact
- Architect: StarPunk Architect
- Issue: Production 500 error on /admin/dashboard
- Priority: CRITICAL
- Timeline: Immediate deployment required