ADR-011: Dynamic Route Error Handling
Defensive error handling in all dynamic route files with 404 redirects for undefined props and slug mismatches
Last updated
Status
Accepted
Context
Dynamic routes in Astro (e.g., /blog/[slug].astro) use getStaticPaths() to generate pages at build time. While Astro’s static path generation prevents most runtime errors, edge cases can still occur:
- Development errors: Props may be undefined during development/testing
- Build-time issues: Content collection queries could fail or return unexpected data
- Future refactoring: Changes to data structures might introduce undefined states
- Defensive programming: Following fail-safe principles for production resilience
Without explicit error handling, these edge cases result in:
- Cryptic build failures
- Poor developer experience during debugging
- Potential runtime errors if SSR is ever enabled
Decision
Implement defensive error handling in all dynamic route files with:
- Undefined post check: Redirect to 404 if post data is missing
- Slug mismatch validation: Handle cases where post slug doesn’t match URL parameter
- Boundary condition comments: Document null handling for prev/next navigation
- Early returns: Use Astro’s redirect for graceful failure
Implementation Pattern
const { post } = Astro.props;
// Error handling: Redirect to 404 if post is undefinedif (!post) { return Astro.redirect("/404");}
// ... fetch related data ...
const currentIndex = allPosts.findIndex((p) => p.slug === post.slug);
// Edge case: If slug mismatch (should not happen with static paths, but defensive)if (currentIndex === -1) { return Astro.redirect("/404");}
// Get previous and next posts (null if at boundaries)const prevPost = currentIndex > 0 ? allPosts[currentIndex - 1] : null;const nextPost = currentIndex < allPosts.length - 1 ? allPosts[currentIndex + 1] : null;Rationale
Why This Approach?
- Fail-safe design: Gracefully handles unexpected states rather than crashing
- Developer experience: Clear error messages via 404 page instead of build failures
- Production resilience: Prevents edge cases from breaking the entire site
- Future-proof: Protects against refactoring errors or data structure changes
- Minimal overhead: Zero runtime cost for static builds (checks happen at build time)
Why Not Alternative Approaches?
Alternative 1: Throw errors
if (!post) throw new Error("Post not found");❌ Breaks build process, poor user experience
Alternative 2: Silent fallback
const post = Astro.props.post ?? defaultPost;❌ Masks bugs, creates confusing behavior
Alternative 3: No error handling
const { post } = Astro.props; // Trust getStaticPaths❌ Fragile during development, no safety net
Consequences
Positive
- ✅ Resilience: Graceful degradation for edge cases
- ✅ DX: Clear 404 pages instead of cryptic build errors
- ✅ Maintainability: Explicit error handling documents assumptions
- ✅ Debugging: Easier to trace issues with explicit checks
- ✅ Zero cost: No runtime overhead for static builds
Neutral
- Slightly more verbose code (4-6 extra lines per dynamic route)
- Requires consistent application across all dynamic routes
Negative
- None identified - this is a pure improvement following defensive programming principles
Compliance
- User Rules: ✅ Follows minimal, focused edits principle
- User Rules: ✅ Uses comments to document edge cases
- User Rules: ✅ Implements defensive programming without over-engineering
- Performance: ✅ Zero runtime overhead (build-time only)
- Accessibility: ✅ Redirects to proper 404 page with ARIA labels
Implementation Checklist
Apply this pattern to all dynamic routes:
-
/src/pages/blog/[slug].astro -
/src/pages/projects/[slug].astro(if applicable) - Any future dynamic routes
Related Files
src/pages/blog/[slug].astro- Primary implementationsrc/pages/404.astro- Error destinationsrc/layouts/BlogLayout.astro- Handles null prev/next gracefully
Future Considerations
- Monitor build logs for 404 redirects (indicates data issues)
- Consider adding build-time validation for content collections
- If SSR is enabled, add runtime error logging
- Add integration tests for error handling paths
References
- Astro Dynamic Routes
- Astro Redirects
- Defensive Programming Principles
Date: 2025-10-01 (footer backfilled 2026-07-05 from git history; this record predates the footer convention)
Participants: Template maintainers
Outcome: Accepted